{"id":25513546,"url":"https://github.com/rajahlone/dosfs.ldg","last_synced_at":"2025-12-01T11:30:14.745Z","repository":{"id":245573603,"uuid":"818654623","full_name":"RajahLone/dosfs.ldg","owner":"RajahLone","description":"Library using the LDG system and the dosfs functions, only for floppy disks images","archived":false,"fork":false,"pushed_at":"2024-12-29T19:13:07.000Z","size":206,"stargazers_count":1,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"master","last_synced_at":"2024-12-29T20:20:05.870Z","etag":null,"topics":["atari-st"],"latest_commit_sha":null,"homepage":"https://ptonthat.fr/dosfs-ldg/","language":"C","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/RajahLone.png","metadata":{"files":{"readme":"README-dosfs.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2024-06-22T13:12:41.000Z","updated_at":"2024-12-29T19:13:10.000Z","dependencies_parsed_at":null,"dependency_job_id":"ed8b84ae-fcba-48f7-b6de-941d3bb25095","html_url":"https://github.com/RajahLone/dosfs.ldg","commit_stats":null,"previous_names":["rajahlone/dosfs.ldg"],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/RajahLone%2Fdosfs.ldg","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/RajahLone%2Fdosfs.ldg/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/RajahLone%2Fdosfs.ldg/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/RajahLone%2Fdosfs.ldg/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/RajahLone","download_url":"https://codeload.github.com/RajahLone/dosfs.ldg/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":239647603,"owners_count":19674200,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["atari-st"],"created_at":"2025-02-19T11:28:22.620Z","updated_at":"2025-12-01T11:30:14.688Z","avatar_url":"https://github.com/RajahLone.png","language":"C","funding_links":[],"categories":[],"sub_categories":[],"readme":"README.TXT                                         (C) Copyright 2006\r\nDOSFS Level 1 Version 1.02      Lewin A.R.W. Edwards (sysadm@zws.com)\r\n=====================================================================\r\n\r\nAbstract\r\n========\r\nDOSFS is a FAT-compatible filesystem intended for fairly low-end\r\nembedded applications. It is not the leanest possible implementation\r\n(the leanest FAT implementations operate in \u003c\u003c 512 bytes of RAM, with\r\nheavy restrictions). This code strikes a good balance between size\r\nand functionality, with an emphasis on RAM footprint.\r\n\r\nIntended target systems would be in the ballpark of 1K RAM, 4K ROM\r\nor more.\r\n\r\nFeatures:\r\n* Supports FAT12, FAT16 and FAT32 volumes\r\n* Supports storage devices up to 2048Gbytes in size (LBA32)\r\n* Supports devices with or without MBRs (hard disks vs. floppy disks\r\n  or ZIP drives formatted as \"big floppies\")\r\n* Supports multiple partitions on disks with MBRs\r\n* Supports subdirectories\r\n* Can be operated with a single global 512-byte sector buffer\r\n* Fully reentrant code (assuming the underlying physical device driver\r\n  is reentrant and global sector buffers are not used). There are no\r\n  global variables in the filesystem\r\n* Does not perform any memory allocation\r\n* Partial support for random-access files\r\n\r\nApplications:\r\n* Firmware upgrades\r\n* Failsafe IPL\r\n* Media playback\r\n* Data logging\r\n* Configuration storage\r\n\r\nThere is no technical support for this free product; however, if you\r\nhave questions or suggestions, you are encouraged to email Lewin\r\nEdwards at sysadm@zws.com. If you need custom additions to the code,\r\nor if you have other projects for which you need engineering\r\nassistance, please feel free to email or call (646) 549-3715.\r\n\r\nLicense\r\n=======\r\nThe license for DOSFS is very simple but verbose to state.\r\n\r\n1. DOSFS is (C) Copyright 2006 by Lewin A.R.W. Edwards (\"Author\").\r\n   All rights not explicitly granted herein are reserved. The DOSFS\r\n   code is the permanent property of the Author and no transfer of\r\n   ownership is implied by this license.\r\n\r\n2. DOSFS is an educational project, provided as-is. No guarantee of\r\n   performance or suitability for any application is stated or\r\n   implied. You use this product entirely at your own risk. Use of\r\n   this product in any manner automatically waives any right to seek\r\n   compensation or damages of any sort from the Author.\tSince the\r\n   products you might make are entirely out of the Author's control,\r\n   use of this product also constitutes an agreement by you to take\r\n   full responsibility for and indemnify the Author against any\r\n   action for any loss or damage (including economic loss of any\r\n   type, and specifically including patent litigation) that arises\r\n   from a product made by you that incorporates any portion of\r\n   the DOSFS code.\r\n\r\n3. If you live under the jurisdiction of any legislation that would\r\n   prohibit or limit any condition in this license, you cannot be\r\n   licensed to use this product.\r\n\r\n4. If you do not fall into the excluded category in point 3, you are\r\n   hereby licensed to use the DOSFS code in any application that you\r\n   see fit. You are not required to pay any fee or notify the Author\r\n   that you are using DOSFS. Any modifications made by you to the\r\n   DOSFS code are your property and you may distribute the modified\r\n   version in any manner that you wish. You are not required to\r\n   disclose sourcecode to such modifications, either to the Author or\r\n   to any third party. Any such disclosure made to the Author will\r\n   irrevocably become the property of the Author in the absence of a\r\n   formal agreement to the contrary, established prior to such\r\n   disclosure being made.\r\n\r\nTo summarize the intent of the above: DOSFS is free. You can do what\r\nyou want with it. Anything that happens as a result is entirely your\r\nresponsibility. You can't take ownership of my code and stop me from\r\ndoing whatever I want with it. If you do something nifty with DOSFS\r\nand send me the sourcecode, I may include your changes in the next\r\ndistribution and it will be released to the world as free software.\r\nIf someone sues you because your DOSFS-containing product causes\r\nany sort of legal, financial or other problem, it's your lawsuit,\r\nnot mine, and you'll exclude me from the proceedings.\r\n\r\nUser-Supplied Functions\r\n=======================\r\nYou must provide functions to read sectors into memory and write\r\nthem back to the target media. The demo suite includes an emulation\r\nmodule that reads/writes a disk image file (#define HOSTVER pulls\r\nin hostemu.h which wraps the prototypes for these functions).\r\nThere are various tools for UNIX, DOS, Windows et al, to create\r\nimages from storage media; my preferred utility is dd.\r\n\r\nThe functions you must supply in your embedded app are:\r\n\r\nDFS_ReadSector(unit,buffer,sector,count)\r\nDFS_WriteSector(unit,buffer,sector,count)\r\n\r\nThese two functions read and write, respectively, \"count\" sectors of\r\nsize SECTOR_SIZE (512 bytes; see below) from/to physical sector\r\n#\"sector\" of device \"unit\", to/from the scratch buffer \"buffer\". They\r\nshould return 0 for success or nonzero for failure. In the current\r\nimplementation of DOSFS, count will always be 1.\r\n\r\nThe \"unit\" argument is designed to permit implementation of multiple\r\nstorage devices, for example multiple media slots on a single device,\r\nor to differentiate between master and slave devices on an ATAPI bus.\r\n\t\t \r\nThis code is designed for 512-byte sectors. Although the sector size\r\nis a #define, you should not tinker with it because the vast majority\r\nof FAT filesystems use 512-byte sectors, and the DOSFS code doesn't\r\nsupport runtime determination of sector size. This will not affect the\r\nvast majority of users.\r\n\r\nExample Code\r\n============\r\nRefer to the tests in main.c to see how to call DOSFS functions.\r\n(These tests are all commented out). Note that the only two files\r\nyou need to add to your project are dosfs.c and dosfs.h.\r\n\r\n\r\nMounting Volumes\r\n================\r\n--If the device has a partition table (practically all removable flash\r\n  media are formatted this way), call DFS_GetPtnStart to get the\r\n  starting sector# of the desired partition. You can optionally also\r\n  retrieve the active state, partition type byte and partition size\r\n  in this step. The reason this step is broken out separately is so\r\n  you can support devices that are formatted like a floppy disk, i.e.\r\n  the volume starts directly at physical sector 0 of the media.\r\n\r\n--Call DFS_GetVolInfo to read filesystem info into a VOLINFO structure.\r\n  DFS_GetVolInfo needs to know the unit number and partition starting\r\n  sector (as returned by DFS_GetPtnStart, or 0 if this is a \"floppy-\r\n  format\" volume without an MBR).\r\n\r\nFrom this point on, the VOLINFO structure is all you'll need - you can\r\nforget the unit and partition start sector numbers.\r\n\r\nEnumerating Directory Contents\r\n==============================\r\n--Call DFS_Opendir and supply a path, populated VOLINFO and a\r\n  DIRINFO structure to receive the results. Note - you must PREPOPULATE\r\n  the DIRINFO.scratch field with a pointer to a sector scratch buffer.\r\n  This buffer must remain unmolested while you have the directory open\r\n  for searching.\r\n--Call DFS_GetNext to receive the DIRENT contents for the next directory\r\n  item. This function returns DFS_OK for no error, and DFS_EOF if there\r\n  are no more entries in the directory being searched.\r\n  Before using the DIRENT, check the first character of the name. If it\r\n  is NULL, then this is an unusable entry - call DFS_GetNext again to\r\n  keep searching. LFN directory entries are automatically tagged this way\r\n  so your application will not be pestered by them.\r\n\r\n  Note: A designed side-effect of this code is that when you locate the\r\n  file of interest, the DIRINFO.currentcluster, DIRINFO.currentsector\r\n  and DIRINFO.currententry-1 fields will identify the directory entry of\r\n  interest.\r\n\r\nReading a File\r\n==============\r\n--Call DFS_OpenFile with mode = DFS_READ and supply a path and the relevant\r\n  VOLINFO structure. DFS_OpenFile will populate a FILEINFO that can be used\r\n  to refer to the file.\r\n--Optionally call DFS_Seek to set the file pointer. If you attempt to set\r\n  the file pointer past the end of file, the file will NOT be extended. Check\r\n  the FILEINFO.pointer value after DFS_Seek to verify that the pointer is\r\n  where you expect it to be.\r\n--Observe that functionality similar to the \"whence\" parameter of fseek() can\r\n  be obtained by using simple arithmetic on the FILEINFO.pointer and\r\n  FILEINFO.filelen members.\r\n--Call DFS_ReadFile with the FILEINFO you obtained from OpenFile, and a\r\n  pointer to a buffer plus the desired number of bytes to read, and a\r\n  pointer to a sector-sized scratch buffer. The reason a scratch sector is\r\n  required is because the underlying sector read function doesn't know\r\n  about partial reads.\r\n--Note that a file opened for reading cannot be written. If you need r/w\r\n  access, open with mode = DFS_WRITE (see below).\r\n\r\nWriting a file\r\n==============\r\n--Call DFS_OpenFile with mode = DFS_WRITE and supply a path and the relevant\r\n  VOLINFO structure. DFS_OpenFile will populate a FILEINFO that can be used to\r\n  refer to the file.\r\n--Optionally call DFS_Seek to set the file pointer. Refer to the notes on\r\n  this topic in the section on reading files, above.\r\n--Call DFS_WriteFile with the FILEINFO you obtained from OpenFile, and a\r\n  pointer to the source buffer, and a pointer to a sector-sized scratch\r\n  buffer.\r\n--Note that a file open for writing can also be read.\r\n--Files are created automatically if they do not exist. Subdirectories are\r\n  NOT automatically created.\r\n--If you open an existing file for writing, the file pointer will start at\r\n  the beginning of the data; if you want to append, seek to the end before\r\n  writing new data.\r\n--If you perform random-access writes to a file, the length will NOT change\r\n  unless you exceed the file's original length. There is currently no\r\n  function to truncate a file at the current pointer position.\r\n--On-disk consistency is guaranteed when DFS_WriteFile exits, unless your\r\n  physical layer has a writeback cache in it.\r\n\r\nDeleting a file\r\n===============\r\n--Call DFS_UnlinkFile\r\n--WARNING: This call will delete a subdirectory (correctly) but will NOT\r\n  first recurse the directory to delete the contents - so you will end up\r\n  with lost clusters.\r\n\r\nNotes\r\n=====\r\nSome platforms may require explicit pragmas or attributes to the structures\r\nand unions. For example, arm-gcc will require __attribute__ ((__packed__))\r\notherwise it will try to be \"smart\" and place the uint8_t members on 4-byte\r\nboundaries. There is no truly elegant compiler-independent method to get\r\naround this sort of problem.\r\n\r\nThe code assumes either a von Neumann architecture, or a compiler that\r\nis smart enough to understand where your pointers are aimed and emit\r\nthe right kind of memory read and write instructions. The implications\r\nof this statement depend on your target processor and the compiler you\r\nare using. Be very careful not to straddle bank boundaries on bank-\r\nswitched memory systems.\r\n\r\nPhysical 32-bit sector numbers are used throughout. Therefore, the\r\nCHS geometry (if any) of the storage media is not known to DOSFS. Your\r\nsector r/w functions may need to query the CHS geometry and perform\r\nmapping.\r\n\r\nFile timestamps set by DOSFS are always 1:01:00am on Jan 1, 2006. If\r\nyour system has a concept of real time, you can enhance this.\r\n\r\nFILEINFO structures contain a pointer to the corresponding VOLINFO\r\nused to open the file, mainly in order to avoid mixups but also to\r\nobviate the need for an extra parameter to every file read/write. DOSFS\r\nassumes that the VOLINFO won't move around. If you need to move or\r\ndestroy VOLINFOs pertaining to open files, you'll have to fix up the\r\npointer in the FILEINFO structure yourself.\r\n\r\nThe subdirectory delimiter is a forward slash ( '/' ) by default. The\r\nreason for this is to avoid the common programming error of forgetting\r\nthat backslash is an escape character in C strings; i.e. \"\\MYDIR\\FILE\"\r\nis NOT what you want; \"\\\\MYDIR\\\\FILE\" is what you wanted to type. If you\r\nare porting DOS code into an embedded environment, feel free to change\r\nthis #define.\r\n\r\nDOSFS does not have a concept of \"current directory\". A current directory\r\nis owned by a process, and a process is an operating system concept.\r\nDOSFS is a filesystem library, not an operating system. Therefore, any\r\npath you provide to a DOSFS call is assumed to be relative to the root of\r\nthe volume.\r\n\r\nThere is no call to close a file or directory that is open for reading or\r\nwriting. You can simply destroy or reuse the data structures allocated for\r\nthat operation; there is no internal state in DOSFS so no cleanup is\r\nnecessary. Similarly, there is no call to close a file that is open for\r\nwriting. (Observe that dosfs.c has no global variables. All state information\r\nis stored in data structures provided by the caller).\r\n\r\nMAX_PATH is defined as 64. MS-type DOS filesystems support 128 characters\r\nor more in paths. You can increase this define, but it may GREATLY\r\nincrease memory requirements.\r\n\r\nVFAT long filenames are not supported. There is a certain amount of\r\npatent controversy about them, but more importantly they don't really\r\nbelong in the scope of a \"minimalist embedded filesystem\".\r\n\r\nImproving Performance\r\n=====================\r\nRead performance is fairly good, but can be improved by implementing read\r\ncaching on the FAT (see below) and, depending on your hardware platform,\r\npossibly by implementing multi-sector reads.\r\n\r\nWrite performance may benefit ENORMOUSLY from platform-specific\r\noptimization, especially if you are working with a flash media type that\r\nhas a large erase block size. While it is not possible to offer detailed\r\nplatform-independent advice, my general advice is to implement writeback\r\ncaching on the FAT area. One method for doing this would be to have a\r\ncache system that lives in the DFS_ReadSector/WriteSector functions (on\r\ntop of the physical sector r/w functions) and is initially switched off.\r\nOnce you have called DFS_GetVolInfo, you then extract the VOLINFO.fat1\r\nand VOLINFO.rootdir parameters and pass them to your caching layer.\r\nSectors \u003e= fat1 and \u003c rootdir should be cached. The cache strategy is\r\ndetermined by the physical storage medium underlying the filesystem.\r\n\r\nCACHING HINT:\r\nObserve that there will be numerous read-modify-write operations in the\r\nregion from VOLINFO.fat1 through VOLINFO.fat1+VOLINFO.secperfat-1, but\r\nin the region from VOLINFO.fat1+VOLINFO.secperfat through VOLINFO.rootdir\r\nthere will ONLY be write operations.\r\n\r\nPlatform Compatibility\r\n======================\r\nDOSFS was derived from code originally written for ARM7TDMI but\r\ndesigned to be portable. It has been tested on AVR (using avrgcc),\r\nMSP430 (using Rowley's CrossWorks) and PPC603e (using gcc); the host\r\ntest suite has also been validated on x86 using gcc under both Cygwin\r\nand 32-bit Fedora Core 4 Linux.\r\n\r\nTODO list\r\n=========\r\n* Add function to create subdirectory\r\n* Make DFS_UnlinkFile recognize non-empty subdirectories\r\n* Support \"fast write\" files where the FAT is not updated, for\r\n  logging applications where latency is important.\r\n\r\nTest cases for V1.02\r\n====================\r\nVersion 1.02 has NOT been through full regression testing. However the\r\nbugs fixed in this version are important, and people have been asking\r\nabout them.\r\n\r\nTest cases for V1.01\r\n====================\r\nSee below.\r\n\r\nTest cases for V1.00\r\n====================\r\nThese are the test cases that were used to validate the correct\r\nfunctionality of the DOSFS suite. Each test was performed on FAT12,\r\nFAT16 and FAT32 volumes. P=Pass, F=Fail.\r\n\r\nCase                                                      F12 F16 F32\r\n---------------------------------------------------------------------\r\nGet volume information                                    P   P   P\r\nOpen root directory                                       P   P   P\r\nList contents of root directory (fully populated)         P   P   P\r\nOpen subdirectory                                         P   P   P\r\nList contents of subdirectory (\u003c= 1 cluster)              P   P   P\r\nList contents of large subdirectory (\u003e 1 cluster)         P   P   P\r\nOpen 5-level nested subdirectory                          P   P   P\r\nOpen existing file for reading                            P   P   P\r\nOpen nonexistent file for reading                         P   P   P\r\nSeek past EOF, file open for reading                      P   P   P\r\nSeek to cluster boundary                                  P   P   P\r\nSeek past cluster boundary                                P   P   P\r\nSeek backwards to nonzero offset, pointer \u003e cluster size  P   P   P\r\nBlock-read entire file \u003e1 cluster in size, odd size       P   P   P\r\nSeek to odd location in file                              P   P   P\r\nPerform \u003c1 sector reads from random file locations        P   P   P\r\nOpen nonexistent file for writing in root dir             P   P   P\r\nOpen nonexistent file for writing in subdir               P   P   P\r\nRepeat prev. 2 tests on volume with 0 free clusters       P   P   P\r\nSeek past EOF, file open for writing                      P   P   P\r\nOpen existing file for writing in root dir                P   P   P\r\nWrite random-length records to file, 20 clusters total    P   P   P\r\nMS-DOS 6.0 SCANDISK cross-check                           P   P   P\r\n\r\nRevision History\r\n================\r\nJan-06-2005 larwe Initial release (1.0)\r\nJan-29-2006 larwe Bugfix release (1.01)\r\n - Fixed error in FAT12 FAT read on boundary of sector\r\n - Improved compilability under avrgcc\r\nSep-16-2006 larwe Bugfix release (1.02)\r\n - DFS_Seek would not correctly rewind to start of file\r\n - DFS_Seek would not correctly seek to a position not on a cluster\r\n   boundary\r\n - DFS_OpenFile fencepost error caused memory access at [start of\r\n   string-1] with a local variable\r\n - DFS_OpenFile could not open a file in the root directory\r\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Frajahlone%2Fdosfs.ldg","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Frajahlone%2Fdosfs.ldg","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Frajahlone%2Fdosfs.ldg/lists"}