Browse Source

Merge pull request #5172 from krnowak/krnowak/sys-linux-dirent-docs

sys/linux: Improve documentation for Dirent and related procedures
Laytan 3 months ago
parent
commit
d3221425a7
2 changed files with 51 additions and 19 deletions
  1. 1 1
      core/sys/linux/types.odin
  2. 50 18
      core/sys/linux/wrappers.odin

+ 1 - 1
core/sys/linux/types.odin

@@ -288,7 +288,7 @@ Rename_Flags :: bit_set[Rename_Flags_Bits; u32]
 
 /*
 	Directory entry record.
-	Recommended iterate these with `dirent_iterator()`,
+	Recommended to iterate these with `dirent_iterate_buf()`,
 	and obtain the name via `dirent_name()`.
 */
 Dirent :: struct {

+ 50 - 18
core/sys/linux/wrappers.odin

@@ -54,22 +54,45 @@ WCOREDUMP :: #force_inline proc "contextless" (s: u32) -> bool {
 // TODO: sigaddset etc
 
 
-/// Iterate the results of getdents
-/// Only iterates as much data as loaded in the buffer
-/// In case you need to iterate *all* files in a directory
-/// consider using dirent_get_iterate
-///
-/// Example of using dirent_iterate_buf
-///   // Get dirents into a buffer
-///   buf: [128]u8
-///   sys.getdents(dirfd, buf[:])
-///   // Print the names of the files
-///   for dir in sys.dirent_iterate_buf(buf[:], &offs) {
-///       name := sys.dirent_name(dir)
-///       fmt.println(name)
-///   }
-/// This function doesn't automatically make a request
-/// for the buffer to be refilled
+/*
+Iterate the results of `getdents()`.
+
+This procedure extracts a directory entry from `buf` at the offset `offs`.
+`offs` will be modified to store an offset to the possible next directory entry
+in `buf`. The procedure only iterates as much data as loaded in the buffer and
+does not automatically make a request for the buffer to be refilled.
+
+Inputs:
+- buf: A byte buffer with data from `getdents()`
+- offs: An offset to the next possible directory entry in `buf`
+
+Returns:
+- A pointer to a directory entry in `buf`, or `nil`
+- A bool value denoting if a valid directory entry is returned
+
+Example:
+
+    import "core:fmt"
+    import "core:sys/linux"
+
+    print_names :: proc(dirfd: linux.Fd) {
+        // Get dirents into a buffer.
+        buf: [128]u8
+        // Loop until there are no more entries.
+        for {
+            written, err := linux.getdents(dirfd, buf[:])
+            if err != .NONE || written == 0 {
+                break
+            }
+            // Print the names of the files.
+            offset : int
+            for dir in linux.dirent_iterate_buf(buf[:written], &offset) {
+                name := linux.dirent_name(dir)
+                fmt.println(name)
+            }
+        }
+    }
+*/
 dirent_iterate_buf :: proc "contextless" (buf: []u8, offs: ^int) -> (d: ^Dirent, cont: bool) {
 	// Stopped iterating when there's no space left
 	if offs^ >= len(buf) {
@@ -82,8 +105,17 @@ dirent_iterate_buf :: proc "contextless" (buf: []u8, offs: ^int) -> (d: ^Dirent,
 	return dirent, true
 }
 
-/// Obtain the name of dirent as a string
-/// The lifetime of the string is bound to the lifetime of the provided dirent structure
+/*
+Obtain the name of dirent as a string.
+
+The lifetime of the returned string is bound to the lifetime of the provided dirent structure.
+
+Inputs:
+- dirent: A directory entry
+
+Returns:
+- A name of the entry
+*/
 dirent_name :: proc "contextless" (dirent: ^Dirent) -> string #no_bounds_check {
 	str := ([^]u8)(&dirent.name)
 	// Dirents are aligned to 8 bytes, so there is guaranteed to be a null