Bug 8558 - Some valid config files give errors when folders are deleted
Summary: Some valid config files give errors when folders are deleted
Status: CLOSED FIXED
Alias: None
Product: ThinLinc
Classification: Unclassified
Component: Misc (show other bugs)
Version: trunk
Hardware: PC Unknown
: P2 Normal
Target Milestone: 4.19.0
Assignee: Samuel Mannehed
URL:
Keywords: aleze_tester, prosaic
Depends on:
Blocks:
 
Reported: 2025-03-27 16:40 CET by Samuel Mannehed
Modified: 2025-04-01 16:48 CEST (History)
1 user (show)

See Also:
Acceptance Criteria:
MUST * It must be safe to delete any valid hiveconf folder


Attachments

Description Samuel Mannehed cendio 2025-03-27 16:40:14 CET
Deleting a folder sometimes gives this traceback:

> 2025-03-27 10:25:37,310: Hiveconf migration option: parameters
> 2025-03-27 10:25:37,351:   /vsmserver/allowed_shadowers removed
> 2025-03-27 10:25:37,351:   /vsmserver/terminalservers removed
> 2025-03-27 10:25:37,351:   /vsmserver/explicit_agentselection removed
> 2025-03-27 10:25:37,352:   /vsmserver/subclusters/Default migrated to /subclusters/Default
> 2025-03-27 10:25:37,354: Traceback (most recent call last):
> 2025-03-27 10:25:37,354:   File "/opt/thinlinc/sbin/../libexec/tl-setup.py", line 329, in <module>
> 2025-03-27 10:25:37,354:     oOoO00 ( )
> 2025-03-27 10:25:37,354:     ~~~~~~~^^^
> 2025-03-27 10:25:37,354:   File "/opt/thinlinc/sbin/../libexec/tl-setup.py", line 285, in oOoO00
> 2025-03-27 10:25:37,354:     O0 = ooOo00oOo0Ooo . run ( )
> 2025-03-27 10:25:37,354:   File "/opt/thinlinc/modules/thinlinc/wizard.py", line 184, in run
> 2025-03-27 10:25:37,354:     return self . _run_text ( )
> 2025-03-27 10:25:37,354:            ~~~~~~~~~~~~~~~~~^^^
> 2025-03-27 10:25:37,354:   File "/opt/thinlinc/modules/thinlinc/wizard.py", line 202, in _run_text
> 2025-03-27 10:25:37,355:     iiiiII11II ( )
> 2025-03-27 10:25:37,355:     ~~~~~~~~~~~^^^
> 2025-03-27 10:25:37,355:   File "/opt/thinlinc/modules/thinlinc/tlsetup/migrate_conf.py", line 494, in oo0o0O0O0OOoO
> 2025-03-27 10:25:37,355:     if not Oo0oO0O0O ( ) :
> 2025-03-27 10:25:37,355:            ~~~~~~~~~~^^^
> 2025-03-27 10:25:37,355:   File "/opt/thinlinc/modules/thinlinc/tlsetup/migrate_conf.py", line 175, in Oo0oO0O0O
> 2025-03-27 10:25:37,355:     i1iII1 ( )
> 2025-03-27 10:25:37,355:     ~~~~~~~^^^
> 2025-03-27 10:25:37,355:   File "/opt/thinlinc/modules/thinlinc/tlsetup/migrate_conf.py", line 197, in i1iII1
> 2025-03-27 10:25:37,355:     ii1I ( O00OoO0OOO0 )
> 2025-03-27 10:25:37,355:     ~~~~~^^^^^^^^^^^^^^^
> 2025-03-27 10:25:37,355:   File "/opt/thinlinc/modules/thinlinc/tlsetup/migrate_conf.py", line 260, in ii1I
> 2025-03-27 10:25:37,355:     hive . delete ( "/vsmserver/subclusters" , recursive = True )
> 2025-03-27 10:25:37,355:     ~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> 2025-03-27 10:25:37,355:   File "/opt/thinlinc/modules/thinlinc/hiveconf.py", line 437, in delete
> 2025-03-27 10:25:37,355:     return parentfolder._delete_folder(comps[-1])
> 2025-03-27 10:25:37,355:            ~~~~~~~~~~~~~~~~~~~~~~~~~~~^^^^^^^^^^^
> 2025-03-27 10:25:37,355:   File "/opt/thinlinc/modules/thinlinc/hiveconf.py", line 449, in _delete_folder
> 2025-03-27 10:25:37,355:     self._folders[foldername]._write_delete_section()
> 2025-03-27 10:25:37,355:     ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~^^
> 2025-03-27 10:25:37,355:   File "/opt/thinlinc/modules/thinlinc/hiveconf.py", line 368, in _write_delete_section
> 2025-03-27 10:25:37,355:     return hfu.delete_section(self.sectionname)
> 2025-03-27 10:25:37,355:            ~~~~~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^
> 2025-03-27 10:25:37,355:   File "/opt/thinlinc/modules/thinlinc/hiveconf.py", line 897, in delete_section
> 2025-03-27 10:25:37,355:     f.seek(section_offset)
> 2025-03-27 10:25:37,355:     ~~~~~~^^^^^^^^^^^^^^^^
> 2025-03-27 10:25:37,355: TypeError: '<' not supported between instances of 'NoneType' and 'int'
Comment 9 Samuel Mannehed cendio 2025-03-31 10:25:56 CEST
Fixed now. Some cleanup was done and FIXME's were fixed as well. Tested on Fedora 41.

> MUST
> 
> * It must be safe to delete any valid hiveconf folder
The case found in migrate_conf no longer crashes.
Comment 10 Alexander Zeijlon cendio 2025-03-31 14:19:20 CEST
I found a scenario that reproduces the stack trace in comment 0:

> [ /first]
> data1=1
> 
> [/first/second]
> data2=2

Note the leading space before the path on the parent folder definition.
Comment 11 Alexander Zeijlon cendio 2025-03-31 14:34:16 CEST
Verify:
=======

Hivetool no longer crashes when a slightly malformed folder structure is removed from the hive.

The behavior, however, is still a bit weird. When recursively removing the folder structure (see comment 10) by calling delete("/first"), everything but the root folder, " /first" is removed.

This makes it look like we are inconsistent with when to strip white spaces from folder names. Clearly, we are recursively finding "/second" relative to "/first" and "data1=1" relative to " /first". But not " /first" itself.
Comment 12 Alexander Zeijlon cendio 2025-03-31 14:36:49 CEST
I also found that we are not removing comments beginning with ";".
Comment 13 Samuel Mannehed cendio 2025-03-31 15:55:52 CEST
(In reply to Alexander Zeijlon from comment #12)
> I also found that we are not removing comments beginning with ";".

True, now fixed as part of bug 8557.
https://github.com/astrand/hiveconf/blob/master/doc/hive-file-syntax.txt
Comment 14 Samuel Mannehed cendio 2025-03-31 16:08:30 CEST
(In reply to Alexander Zeijlon from comment #10)
> I found a scenario that reproduces the stack trace in comment 0:
> 
> > [ /first]
> > data1=1
> > 
> > [/first/second]
> > data2=2
> 
> Note the leading space before the path on the parent folder definition.

This is the same as the following configuration:
> [ /otherfolder]
> data1=1
> 
> [/first/second]
> data2=2
There is no strict requirement that a top-level folder must exist for a subfolder to be correct.


(In reply to Alexander Zeijlon from comment #11)
> The behavior, however, is still a bit weird. When recursively removing the
> folder structure (see comment 10) by calling delete("/first"), everything
> but the root folder, " /first" is removed.
No, the result of delete("/first", recursive=True) is:
> [ /first]
> data1=1
I.e, only the folder starting with "/first" is removed. I don't think there is anything wrong with that.
Comment 15 Alexander Zeijlon cendio 2025-03-31 17:23:03 CEST
(In reply to Samuel Mannehed from comment #14)
> No, the result of delete("/first", recursive=True) is:
> > [ /first]
> > data1=1
> I.e, only the folder starting with "/first" is removed. I don't think there
> is anything wrong with that.

I realized what I did differently here. I tried looping over all folders in "/" and then deleted them recursively like so:
> for folder in hive.get_folders('/')[1:]:
>     hive.delete(f'/{folder}', recursive=True)

The space is interpreted as a path component, and thus calling hive.delete("/ ", recursive=True) resulted in "data1=1" being removed while "[ /first]" persists in the file.

I'm not sure if his is correct behavior, but at least I think it is not a part of this bug.
Comment 16 Alexander Zeijlon cendio 2025-04-01 14:05:35 CEST
The stack trace in comment 0, occurs when hivetool tries to remove a folder that does no longer exist in the file on disk [1], so in this scenario:

[1] This is not the same as the scenario I assumed had occurred in comment 10.

somefile.hconf:
> [/some]
> [/some/path]
> data = 1
Load the file in python:
> hive = hiveconf.open_hive("somefile.hconf")
Modify somefile.hconf:
> [/some/path]
> data = 1
Try to delete the folder "/some"
> hive.delete("/some", recursive=True)

Doing this reproduces the stack trace, before the fix. After the fix, the run results in all folders and subfolders of "/some" being removed.
Comment 17 Alexander Zeijlon cendio 2025-04-01 14:07:13 CEST
Looks good to me, closing!

Note You need to log in before you can comment on or make changes to this bug.