Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Usage of os.linesep() creates faulty constrain.inp files in Windows machines #52

Open
dkesada opened this issue Feb 13, 2025 · 0 comments

Comments

@dkesada
Copy link

dkesada commented Feb 13, 2025

Describe the bug
Hi! The constrain.inp files created in Windows machines by using the exchangeSubstructure() method contain an additional blank line after each line, and this renders these files unusable because xtb will simply ignore them without issuing a warning, causing unexpected behaviours.

I found this out after realizing that xtb continuously ignored my attempts at fixing atom positions by inputing the generated constrain.inp file, but when I manually removed these extra blank lines the problem was fixed.

The culprit is the use of os.linesep() when writting the constrain.inp file here, on line 306. This usage of os.linesep() when writting to a file in text mode is discouraged in the Python docs because it does not return what one expects to write in Windows machines, and it should be replaced by a '\n' no matter the platform. Additionally, this issue can also be seen when writting .xyz files on Windows machines, so I would assume that all file writting on the package uses os.linesep() and so empty lines are introduced in these cases. On .xyz files it is not an isse normally, but on input files for xtb it renders them unusable.

To Reproduce
I made a simple reproducible example of this behaviour by exchanging one H of a benzene ring with a cetone. I displaced one of the H atoms in the ring to show how the constrain.inp file is ignored if there are blank lines and it just optimizes the full structure:

  1. On a Windows machine, exchange the substructure of some atom. In my example an H for a cetone in the benzene ring. Here are the xyz of both the ring and the cetone for reproducibility:
12
Benzene with a displaced H to see if it stays put
6        0.000000000      0.000000000      0.000000000
6       -1.023307117      0.600143563      0.741505265
6       -0.987718893      0.586881689      2.142882342
6        0.098220426     -0.034907496      2.785186682
1        0.140336123     -0.051076560      3.872349039
1       -1.852875473      1.072038426      0.224930286
1       -0.045721569      0.014201560     -1.085687019
6        1.075261731     -0.613066180      0.647300169
1        1.866763329     -1.081861695      0.069612888
1        1.958152372     -1.094946490      2.559736963
6        1.124966833     -0.622728915      2.046315052
1       -2.062088256      0.064787042      2.442452687

Image

6
Cetone substructure
6        -4.974753150     -0.487271440     -2.474084540
8        -6.202068490     -0.487270320     -2.472071290
6        -4.153557010     -1.790051890     -2.474030460
1        -3.109957660     -1.553839060     -2.476001160
1        -4.391508070     -2.361689160     -3.346675930
1        -4.388634230     -2.359805730     -1.599376650
  1. Exchange the H on the C11 for example with center_idx=10 and sub_idx=2. We obtain the following xyz and constrain.inp files, which both suffer from the same os.linesep() issue:
   17

Created with kallisto

C      0.0000    0.0000    0.0000

C     -1.0233    0.6001    0.7415

C     -0.9877    0.5869    2.1429

C      0.0982   -0.0349    2.7852

H      0.1403   -0.0511    3.8723

H     -1.8529    1.0720    0.2249

H     -0.0457    0.0142   -1.0857

C      1.0753   -0.6131    0.6473

H      1.8668   -1.0819    0.0696

C      1.1250   -0.6227    2.0463

H     -2.0621    0.0648    2.4425

C      1.9582   -1.0949    2.5597

O      2.9030   -0.3127    2.5190

C      2.0596   -2.4702    3.2453

H      1.1232   -2.9809    3.1606

H      2.3007   -2.3365    4.2791

H      2.8255   -3.0488    2.7724

$fix

 atoms: 1-12

$constrain

 distance: 12, 13, auto

 distance: 12, 14, auto

 distance: 13, 12, auto

 distance: 14, 12, auto

 distance: 14, 15, auto

 distance: 14, 16, auto

 distance: 14, 17, auto

 distance: 15, 14, auto

 distance: 16, 14, auto

 distance: 17, 14, auto

$end

  1. The generated constrain.inp file has additional blank lines inbetween each line, and if we launch an xtb optimization like xtb .\new_complex.xyz --input .\constrain.inp --opt tight --alpb thf that uses these files, the constrain.inp file gets ignored without warnings and the whole molecule gets optimized, which can be seen clearly by the displaced H atom being moved into place
17
 energy: -25.261166004187 gnorm: 0.000232506916 xtb: 6.7.1pre (5071a88)
C            0.00914806069615        0.40150946731128       -0.03094417051955
C           -1.10446026568403        0.63967440573588        0.75979255272343
C           -1.15255207926867        0.14377142356296        2.05370025415221
C           -0.09590903568220       -0.58929238100835        2.56225026017644
H           -0.15377012944768       -0.96494257283060        3.57102700925024
H           -1.93280509946461        1.21143672462219        0.36906132620738
H            0.05162884742455        0.78555253955894       -1.03911125968268
C            1.06692732462028       -0.32904798638890        0.47386392572310
H            1.94320815225801       -0.52530925205547       -0.12661165582234
C            1.03029525180407       -0.83511246765737        1.77559047956757
H           -2.01998208425935        0.33050321295509        2.66912466313992
C            2.20009765216492       -1.61194095992225        2.25357221822901
O            3.18003500975718       -1.77476382011473        1.54799860199829
C            2.13219023700250       -2.19228839852900        3.64172607139536
H            1.27647881798368       -2.85802486385708        3.72657756302247
H            2.02847742664719       -1.39375238426769        4.37277518127736
H            3.04509191344829       -2.74767268711489        3.84250697916241

Image

  1. Launching the same xtb optimization by manually removing the blank spaces in the constrain.inp file makes the input file not get ignored, and then xtb cannot converge to a solution and throws error due optimization failing. But this is what should happen by default, that the constrain.inp file does not get ignored. Fixing the optimization engine to 'lbfgs' instead of the default 'rf' produces the expected results, where the cetone gets optimized but the ring keeps its displaced H atom because the constrain.inp file fixes the ring position:
17
 energy: -24.985859501749 gnorm: 0.007764265696 xtb: 6.7.1pre (5071a88)
C            0.00000000000000        0.00000000000000        0.00000000000000
C           -1.02330000000000        0.60010000000000        0.74150000000000
C           -0.98770000000000        0.58690000000000        2.14290000000000
C            0.09820000000000       -0.03490000000000        2.78520000000000
H            0.14030000000000       -0.05110000000000        3.87230000000000
H           -1.85290000000000        1.07200000000000        0.22490000000000
H           -0.04570000000000        0.01420000000000       -1.08570000000000
C            1.07530000000000       -0.61310000000000        0.64730000000000
H            1.86680000000000       -1.08190000000000        0.06960000000000
C            1.12500000000000       -0.62270000000000        2.04630000000000
H           -2.06210000000000        0.06480000000000        2.44250000000000
C            1.95820000000000       -1.09490000000000        2.55970000000000
O            3.07193086831905       -0.52276273560927        2.64899353346637
C            2.05435010005313       -2.47233599650689        3.25188700262860
H            1.16428627539437       -3.07613578737864        3.19907350864713
H            2.34916525191428       -2.28235091628830        4.27476082169920
H            2.89268297234788       -2.96651399364513        2.77810205515009

Image

Expected behavior
Expected behaviour should be the one found in step number 4, where the constrain.inp file is written without blank lines and it does not get ignored by xtb without warnings. Ultimately, using os.linesep() to write the files causes this compatibility issue on Windows machines.

@dkesada dkesada changed the title Usage of _os.linesep()_ creates faulty constrain.inp files in Windows machines Usage of os.linesep() creates faulty constrain.inp files in Windows machines Feb 13, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant