Add file operations
Some checks failed
Build / build (push) Failing after 6m4s
Test / build (push) Has been cancelled

This commit is contained in:
Chuck Smith
2024-03-28 14:00:21 -04:00
parent 110152a139
commit 67c5b4cd66
7 changed files with 226 additions and 3 deletions

86
builtins/open.go Normal file
View File

@@ -0,0 +1,86 @@
package builtins
import (
"fmt"
"log"
"monkey/object"
"monkey/typing"
"os"
"syscall"
)
// Close ...
func parseMode(mode string) (int, error) {
var flag int
for _, c := range mode {
switch c {
case 'r':
if (flag & os.O_WRONLY) != 0 {
flag |= os.O_RDWR
} else {
log.Printf("r2")
flag |= os.O_RDONLY
}
case 'w':
if (flag & os.O_RDONLY) != 0 {
flag |= os.O_RDWR
} else {
flag |= os.O_WRONLY
}
case 'a':
flag |= os.O_APPEND
default:
return 0, fmt.Errorf("ValueError: mode string must be one of 'r', 'w', 'a', not '%c'", c)
}
}
if (flag&os.O_WRONLY) != 0 || (flag&os.O_RDWR) != 0 {
log.Printf("c1")
flag |= os.O_CREATE
if (flag & os.O_APPEND) == 0 {
log.Printf("t1")
flag |= os.O_TRUNC
}
}
if !((flag == os.O_RDONLY) || (flag&os.O_WRONLY != 0) || (flag&os.O_RDWR != 0)) {
return 0, fmt.Errorf("ValueError: mode string must be at least one of 'r', 'w', or 'rw'")
}
return flag, nil
}
// Open ...
func Open(args ...object.Object) object.Object {
if err := typing.Check(
"open", args,
typing.RangeOfArgs(1, 2),
typing.WithTypes(object.STRING_OBJ, object.STRING_OBJ),
); err != nil {
return newError(err.Error())
}
var (
filename string
mode = "r"
perm uint32 = 0640
)
filename = args[0].(*object.String).Value
if len(args) == 2 {
mode = args[1].(*object.String).Value
}
flag, err := parseMode(mode)
if err != nil {
return newError(err.Error())
}
fd, err := syscall.Open(filename, flag, perm)
if err != nil {
return newError("IOError: %s", err)
}
return &object.Integer{Value: int64(fd)}
}