AllenInstitute / MIES

Multichannel Igor Electrophysiology Suite
https://alleninstitute.github.io/MIES/user.html
Other
22 stars 6 forks source link

threadsafe file/folder exists check #570

Open MichaelHuth opened 4 years ago

MichaelHuth commented 4 years ago

GetFileAndFolderInfo is not threadsafe (IP8) which needs another approach for file/folder exists checks. Here is an idea:

static Constant FSYS_ACCESS_DENIED = 30001
static Constant FSYS_NOT_FOUND = -43
static Constant FSYS_NO_ERROR = 0

/// @brief Returns a unique and non-existing file name
///
/// @warning This function must *not* be used for security relevant purposes,
/// as for that the check-and-file-creation must be an atomic operation.
///
/// @param path string path
/// @param baseName  base name of the file, must not be empty
/// @param suffix    file suffix, e.g. ".txt", must not be empty
threadsafe static Function [variable err, string fullFilePath] SAVE_UniqueFile(string path, string baseName, string suffix)

    string file
    variable i, fnum

    path = GetWindowsPath(path)
    file = path + "." // FolderExists check
    Open/R/Z fnum as file
    if(V_flag != FSYS_ACCESS_DENIED)
        return [SAVE_STATUS_ERR, "Save path not found !"]
    endif

    for(i = 0; i < 100000; i += 1)
        sprintf file, "%s%s_%05d.%s", path, baseName, i, suffix
        Open/R/Z fnum as file // FileExists check
        if(V_Flag == FSYS_NOT_FOUND)
            return [SAVE_STATUS_OK, file]
        endif
        if(V_Flag == FSYS_NO_ERROR)
            Close fnum
        endif
    endfor

    return [SAVE_STATUS_ERR, "Could not find unique file name with 100000 tries in save path !"]
End

Idea is that for file open, when trying to open "path." open returns ACCESS_DENIED if it exists and something else like FILE NOT FOUND if it does not. The file check on the other hand checks against FILE NOT FOUND.

t-b commented 2 years ago

Unfortunately our non-threadsafe version of FileExists, https://github.com/AllenInstitute/MIES/blob/ecc71019f46c0643e1674d86d47f33fedb41b610/Packages/MIES/MIES_Utilities.ipf#L5085-5092, has also support for resolving windows lnk files (called aliases in IP). And I don't see a way to do that without GetFileFolderInfo.

timjarsky commented 1 year ago

GetfilefolderInfo is still not threadsafe in IP9. IP10?