opnsense-src/sys/tools/syscalls/core/freebsd-syscall.lua
agge3 9ded074e87 Refactor makesyscalls.lua into a library
* main.lua replicates the functionality of makesyscalls.lua
* Individual files are generated by their associated module
  * Modules can be called as standalone scripts to generate a specific
    file
* Data and procedures are performed by objects instead of procedual code
* Bitmasks are replaced by declarative types
* Temporary files are no longer produced, writing is stored in memory
* Comments provide explanation to functions and semantics

Google Summer of Code 2024 Final Work Product

Co-authored-by: Warner Losh <imp@freebsd.org>
Co-authored-by: Kyle Evans <kevans@freebsd.org>
Co-authored-by: Brooks Davis <brooks@freebsd.org>
Sponsored by:    Google (GSoC 24)
Pull Request:	https://github.com/freebsd/freebsd-src/pull/1362
Signed-off-by: agge3 <sterspark@gmail.com>
2024-10-30 21:04:30 +00:00

147 lines
3.4 KiB
Lua

--
-- SPDX-License-Identifier: BSD-2-Clause
--
-- Copyright (c) 2024 Tyler Baxter <agge@FreeBSD.org>
-- Copyright (c) 2023 Warner Losh <imp@bsdimp.com>
-- Copyright (c) 2019 Kyle Evans <kevans@FreeBSD.org>
--
local syscall = require("core.syscall")
local util = require("tools.util")
local FreeBSDSyscall = {}
FreeBSDSyscall.__index = FreeBSDSyscall
-- For each compat option in the provided config table, process them and insert
-- them into known_flags for class syscall.
function FreeBSDSyscall:processCompat()
for _, v in pairs(self.config.compat_options) do
if v.stdcompat ~= nil then
local stdcompat = v.stdcompat
v.definition = "COMPAT_" .. stdcompat:upper()
v.compatlevel = tonumber(stdcompat:match("([0-9]+)$"))
v.flag = stdcompat:gsub("FREEBSD", "COMPAT")
v.prefix = stdcompat:lower() .. "_"
v.descr = stdcompat:lower()
end
-- Add compat option to syscall.known_flags.
table.insert(syscall.known_flags, v.flag)
end
end
function FreeBSDSyscall:parseSysfile()
local file = self.sysfile
local config = self.config
local commentExpr = "^%s*;.*"
if file == nil then
return nil, "No file given"
end
self.syscalls = {}
local fh, msg = io.open(file)
if fh == nil then
return nil, msg
end
local incs = ""
local defs = ""
local s
for line in fh:lines() do
line = line:gsub(commentExpr, "") -- Strip any comments.
-- NOTE: Can't use pure pattern matching here because of
-- the 's' test and this is shorter than a generic pattern
-- matching pattern.
if line == nil or line == "" then
goto skip -- Blank line, skip this line.
elseif s ~= nil then
-- If we have a partial system call object s,
-- then feed it one more line.
if s:add(line) then
-- Append to system call list.
for t in s:iter() do
if t:validate(t.num - 1) then
table.insert(self.syscalls, t)
else
util.abort(1,
"Skipped system call " ..
"at number " .. t.num)
end
end
s = nil
end
elseif line:match("^#%s*include") then
incs = incs .. line .. "\n"
elseif line:match("%%ABI_HEADERS%%") then
local h = self.config.abi_headers
if h ~= nil and h ~= "" then
incs = incs .. h .. "\n"
end
elseif line:match("^#%s*define") then
defs = defs .. line.. "\n"
elseif line:match("^#") then
util.abort(1, "Unsupported cpp op " .. line)
else
s = syscall:new()
if s:add(line) then
-- Append to system call list.
for t in s:iter() do
if t:validate(t.num - 1) then
table.insert(self.syscalls, t)
else
util.abort(1,
"Skipped system call " ..
"at number " .. t.num)
end
end
s = nil
end
end
::skip::
end
-- Special handling for linux nosys.
if config.syscallprefix:find("LINUX") ~= nil then
s = nil
end
if s ~= nil then
util.abort(1, "Dangling system call at the end")
end
assert(fh:close())
self.includes = incs
self.defines = defs
end
function FreeBSDSyscall:findStructs()
self.structs = {}
for _, s in pairs(self.syscalls) do
if s:native() and not s.type.NODEF then
for _, v in ipairs(s.args) do
local name = util.structName(v.type)
if name ~= nil then
self.structs[name] = name
end
end
end
end
end
function FreeBSDSyscall:new(obj)
obj = obj or {}
setmetatable(obj, self)
self.__index = self
obj:processCompat()
obj:parseSysfile()
obj:findStructs()
return obj
end
return FreeBSDSyscall