Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
freebsd
GitHub Repository: freebsd/freebsd-src
Path: blob/main/sys/tools/syscalls/core/scarg.lua
39530 views
1
--
2
-- SPDX-License-Identifier: BSD-2-Clause
3
--
4
-- Copyright (c) 2021-2024 SRI International
5
-- Copyright (c) 2024 Tyler Baxter <[email protected]>
6
-- Copyright (c) 2023 Warner Losh <[email protected]>
7
-- Copyright (c) 2019 Kyle Evans <[email protected]>
8
--
9
10
local config = require("config")
11
local util = require("tools.util")
12
13
local scarg = {}
14
15
scarg.__index = scarg
16
17
-- Check this argument against config for ABI changes from native. Return TRUE
18
-- if there are.
19
local function checkAbiChanges(arg)
20
for k, v in pairs(config.known_abi_flags) do
21
if config.abiChanges(k) and v ~= nil then
22
for _, e in pairs(v) do
23
if arg:find(e) then
24
return true
25
end
26
end
27
end
28
end
29
return false
30
end
31
32
-- Strips the Microsoft(R) SAL annotations from this argument.
33
local function stripArgAnnotations(arg)
34
arg = arg:gsub("_Contains_[^ ]*[_)] ?", "")
35
arg = arg:gsub("_In[^ ]*[_)] ?", "")
36
arg = arg:gsub("_Out[^ ]*[_)] ?", "")
37
return util.trim(arg)
38
end
39
40
-- Preprocessing of this argument.
41
function scarg:init(line)
42
-- Trim whitespace and trailing comma. We don't want them here;
43
-- these can mess with our processing of this argument.
44
line = util.trim(line) -- This provides a clearer abort error.
45
self.scarg = util.trim(line, ',')
46
47
self.arg_abi_change = checkAbiChanges(self.scarg)
48
self.changes_abi = self.arg_abi_change
49
self.scarg = stripArgAnnotations(self.scarg)
50
51
self.name = self.scarg:match("([^* ]+)$")
52
-- Our pattern might produce a Lua pattern sequence; that's a malformed
53
-- declaration.
54
local status, type = pcall(function()
55
return util.trim(self.scarg:gsub(self.name .. "$", ""), nil)
56
end)
57
if not status then
58
util.abort(1, "Malformed argument line: " .. line)
59
end
60
self.type = type
61
end
62
63
-- Processes this argument.
64
-- Flags if there's ABI changes from native, converts this argument to the
65
-- target ABI, and handles 64-bit argument pairing.
66
-- Returns TRUE if this argument is processed and ready to add.
67
-- Returns FALSE if it shouldn't be added (the argument type is void).
68
function scarg:process()
69
if self.type ~= "" and self.name ~= "void" then
70
-- util.is64bitType() needs a bare type so check it after
71
-- argname is removed.
72
self.changes_abi = self.changes_abi or
73
(config.abiChanges("pair_64bit") and
74
util.is64bitType(self.type))
75
76
self.type = self.type:gsub("intptr_t", config.abi_intptr_t)
77
self.type = self.type:gsub("semid_t", config.abi_semid_t)
78
79
if util.isPtrType(self.type) then
80
self.type = self.type:gsub("size_t", config.abi_size_t)
81
self.type = self.type:gsub("^long", config.abi_long)
82
self.type = self.type:gsub("^u_long", config.abi_u_long)
83
self.type = self.type:gsub("^const u_long", "const " ..
84
config.abi_u_long)
85
elseif self.type:find("^long$") then
86
self.type = config.abi_long
87
end
88
89
if util.isPtrArrayType(self.type) and
90
config.abi_ptr_array_t ~= "" then
91
-- `* const *` -> `**`
92
self.type = self.type:gsub("[*][ ]*const[ ]*[*]", "**")
93
-- e.g., `struct aiocb **` -> `uint32_t *`
94
self.type = self.type:gsub("[^*]*[*]",
95
config.abi_ptr_array_t .. " ", 1)
96
end
97
98
if self.arg_abi_change then
99
self.type = self.type:gsub("(struct [^ ]*)", "%1" ..
100
config.abi_type_suffix)
101
self.type = self.type:gsub("(union [^ ]*)", "%1" ..
102
config.abi_type_suffix)
103
end
104
return true
105
end
106
return false
107
end
108
109
-- For pairing 64-bit arguments, pad if necessary.
110
-- Returns TRUE if this argument was padded.
111
local function pad(tbl)
112
if #tbl % 2 == 1 then
113
table.insert(tbl, {
114
type = "int",
115
name = "_pad",
116
})
117
return true
118
end
119
return false
120
end
121
122
-- To append to a system call's argument table. Appends to the end.
123
function scarg:append(tbl)
124
if config.abiChanges("pair_64bit") and util.is64bitType(self.type) then
125
pad(tbl) -- Needs argument padding.
126
table.insert(tbl, {
127
type = "uint32_t",
128
name = self.name .. "1",
129
})
130
table.insert(tbl, {
131
type = "uint32_t",
132
name = self.name .. "2",
133
})
134
else
135
table.insert(tbl, {
136
type = self.type,
137
name = self.name,
138
})
139
end
140
end
141
142
-- Returns TRUE if this argument has ABI changes from native.
143
-- EXAMPLE: 32-bit argument for freebsd32.
144
function scarg:changesAbi()
145
return self.changes_abi
146
end
147
148
function scarg:new(obj, line)
149
obj = obj or { }
150
setmetatable(obj, self)
151
self.__index = self
152
153
-- ABI changes that we only want in this scope.
154
self.arg_abi_change = false
155
-- ABI changes that we want the system call object to see.
156
self.changes_abi = false
157
158
obj:init(line)
159
160
return obj
161
end
162
163
return scarg
164
165