about summary refs log tree commit diff stats
path: root/src/json.lua
blob: c41ef56bdcd03cfd7d521444960b61b9d168e2be (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
--
-- https://github.com/rxi/json.lua
--
-- Copyright (c) 2020 rxi
--
-- Permission is hereby granted, free of charge, to any person obtaining a copy of
-- this software and associated documentation files (the "Software"), to deal in
-- the Software without restriction, including without limitation the rights to
-- use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
-- of the Software, and to permit persons to whom the Software is furnished to do
-- so, subject to the following conditions:
--
-- The above copyright notice and this permission notice shall be included in all
-- copies or substantial portions of the Software.
--
-- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
-- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
-- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
-- AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
-- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
-- OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
-- SOFTWARE.
--

local json = { _version = "0.1.2" }

-------------------------------------------------------------------------------
-- Encode
-------------------------------------------------------------------------------

local encode

local escape_char_map = {
  [ "\\" ] = "\\",
  [ "\"" ] = "\"",
  [ "\b" ] = "b",
  [ "\f" ] = "f",
  [ "\n" ] = "n",
  [ "\r" ] = "r",
  [ "\t" ] = "t",
}

local escape_char_map_inv = { [ "/" ] = "/" }
for k, v in pairs(escape_char_map) do
  escape_char_map_inv[v] = k
end


local function escape_char(c)
  return "\\" .. (escape_char_map[c] or string.format("u%04x", c:byte()))
end


local function encode_nil(val)
  return "null"
end


local function encode_table(val, stack)
  local res = {}
  stack = stack or {}

  -- Circular reference?
  if stack[val] then error("circular reference") end

  stack[val] = true

  if rawget(val, 1) ~= nil or next(val) == nil then
    -- Treat as array -- check keys are valid and it is not sparse
    local n = 0
    for k in pairs(val) do
      if type(k) ~= "number" then
        error("invalid table: mixed or invalid key types")
      end
      n = n + 1
    end
    if n ~= #val then
      error("invalid table: sparse array")
    end
    -- Encode
    for i, v in ipairs(val) do
      table.insert(res, encode(v, stack))
    end
    stack[val] = nil
    return "[" .. table.concat(res, ",") .. "]"

  else
    -- Treat as an object
    for k, v in pairs(val) do
      if type(k) ~= "string" then
        error("invalid table: mixed or invalid key types")
      end
      table.insert(res, encode(k, stack) .. ":" .. encode(v, stack))
    end
    stack[val] = nil
    return "{" .. table.concat(res, ",") .. "}"
  end
end


local function encode_string(val)
  return '"' .. val:gsub('[%z\1-\31\\"]', escape_char) .. '"'
end


local function encode_number(val)
  -- Check for NaN, -inf and inf
  if val ~= val or val <= -math.huge or val >= math.huge then
    error("unexpected number value '" .. tostring(val) .. "'")
  end
  return string.format("%.14g", val)
end


local type_func_map = {
  [ "nil"     ] = encode_nil,
  [ "table"   ] = encode_table,
  [ "string"  ] = encode_string,
  [ "number"  ] = encode_number,
  [ "boolean" ] = tostring,
}


encode = function(val, stack)
  local t = type(val)
  local f = type_func_map[t]
  if f then
    return f(val, stack)
  end
  error("unexpected type '" .. t .. "'")
end


function json.encode(val)
  return ( encode(val) )
end


-------------------------------------------------------------------------------
-- Decode
-------------------------------------------------------------------------------

local parse

local function create_set(...)
  local res = {}
  for i = 1, select("#", ...) do
    res[ select(i, ...) ] = true
  end
  return res
end

local space_chars   = create_set(" ", "\t", "\r", "\n")
local delim_chars   = create_set(" ", "\t", "\r", "\n", "]", "}", ",")
local escape_chars  = create_set("\\", "/", '"', "b", "f", "n", "r", "t", "u")
local literals      = create_set("true", "false", "null")

local literal_map = {
  [ "true"  ] = true,
  [ "false" ] = false,
  [ "null"  ] = nil,
}


local function next_char(str, idx, set, negate)
  for i = idx, #str do
    if set[str:sub(i, i)] ~= negate then
      return i
    end
  end
  return #str + 1
end


local function decode_error(str, idx, msg)
  local line_count = 1
  local col_count = 1
  for i = 1, idx - 1 do
    col_count = col_count + 1
    if str:sub(i, i) == "\n" then
      line_count = line_count + 1
      col_count = 1
    end
  end
  error( string.format("%s at line %d col %d", msg, line_count, col_count) )
end


local function codepoint_to_utf8(n)
  -- http://scripts.sil.org/cms/scripts/page.php?site_id=nrsi&id=iws-appendixa
  local f = math.floor
  if n <= 0x7f then
    return string.char(n)
  elseif n <= 0x7ff then
    return string.char(f(n / 64) + 192, n % 64 + 128)
  elseif n <= 0xffff then
    return string.char(f(n / 4096) + 224, f(n % 4096 / 64) + 128, n % 64 + 128)
  elseif n <= 0x10ffff then
    return string.char(f(n / 262144) + 240, f(n % 262144 / 4096) + 128,
                       f(n % 4096 / 64) + 128, n % 64 + 128)
  end
  error( string.format("invalid unicode codepoint '%x'", n) )
end


local function parse_unicode_escape(s)
  local n1 = tonumber( s:sub(1, 4),  16 )
  local n2 = tonumber( s:sub(7, 10), 16 )
   -- Surrogate pair?
  if n2 then
    return codepoint_to_utf8((n1 - 0xd800) * 0x400 + (n2 - 0xdc00) + 0x10000)
  else
    return codepoint_to_utf8(n1)
  end
end


local function parse_string(str, i)
  local res = ""
  local j = i + 1
  local k = j

  while j <= #str do
    local x = str:byte(j)

    if x < 32 then
      decode_error(str, j, "control character in string")

    elseif x == 92 then -- `\`: Escape
      res = res .. str:sub(k, j - 1)
      j = j + 1
      local c = str:sub(j, j)
      if c == "u" then
        local hex = str:match("^[dD][89aAbB]%x%x\\u%x%x%x%x", j + 1)
                 or str:match("^%x%x%x%x", j + 1)
                 or decode_error(str, j - 1, "invalid unicode escape in string")
        res = res .. parse_unicode_escape(hex)
        j = j + #hex
      else
        if not escape_chars[c] then
          decode_error(str, j - 1, "invalid escape char '" .. c .. "' in string")
        end
        res = res .. escape_char_map_inv[c]
      end
      k = j + 1

    elseif x == 34 then -- `"`: End of string
      res = res .. str:sub(k, j - 1)
      return res, j + 1
    end

    j = j + 1
  end

  decode_error(str, i, "expected closing quote for string")
end


local function parse_number(str, i)
  local x = next_char(str, i, delim_chars)
  local s = str:sub(i, x - 1)
  local n = tonumber(s)
  if not n then
    decode_error(str, i, "invalid number '" .. s .. "'")
  end
  return n, x
end


local function parse_literal(str, i)
  local x = next_char(str, i, delim_chars)
  local word = str:sub(i, x - 1)
  if not literals[word] then
    decode_error(str, i, "invalid literal '" .. word .. "'")
  end
  return literal_map[word], x
end


local function parse_array(str, i)
  local res = {}
  local n = 1
  i = i + 1
  while 1 do
    local x
    i = next_char(str, i, space_chars, true)
    -- Empty / end of array?
    if str:sub(i, i) == "]" then
      i = i + 1
      break
    end
    -- Read token
    x, i = parse(str, i)
    res[n] = x
    n = n + 1
    -- Next token
    i = next_char(str, i, space_chars, true)
    local chr = str:sub(i, i)
    i = i + 1
    if chr == "]" then break end
    if chr ~= "," then decode_error(str, i, "expected ']' or ','") end
  end
  return res, i
end


local function parse_object(str, i)
  local res = {}
  i = i + 1
  while 1 do
    local key, val
    i = next_char(str, i, space_chars, true)
    -- Empty / end of object?
    if str:sub(i, i) == "}" then
      i = i + 1
      break
    end
    -- Read key
    if str:sub(i, i) ~= '"' then
      decode_error(str, i, "expected string for key")
    end
    key, i = parse(str, i)
    -- Read ':' delimiter
    i = next_char(str, i, space_chars, true)
    if str:sub(i, i) ~= ":" then
      decode_error(str, i, "expected ':' after key")
    end
    i = next_char(str, i + 1, space_chars, true)
    -- Read value
    val, i = parse(str, i)
    -- Set
    res[key] = val
    -- Next token
    i = next_char(str, i, space_chars, true)
    local chr = str:sub(i, i)
    i = i + 1
    if chr == "}" then break end
    if chr ~= "," then decode_error(str, i, "expected '}' or ','") end
  end
  return res, i
end


local char_func_map = {
  [ '"' ] = parse_string,
  [ "0" ] = parse_number,
  [ "1" ] = parse_number,
  [ "2" ] = parse_number,
  [ "3" ] = parse_number,
  [ "4" ] = parse_number,
  [ "5" ] = parse_number,
  [ "6" ] = parse_number,
  [ "7" ] = parse_number,
  [ "8" ] = parse_number,
  [ "9" ] = parse_number,
  [ "-" ] = parse_number,
  [ "t" ] = parse_literal,
  [ "f" ] = parse_literal,
  [ "n" ] = parse_literal,
  [ "[" ] = parse_array,
  [ "{" ] = parse_object,
}


parse = function(str, idx)
  local chr = str:sub(idx, idx)
  local f = char_func_map[chr]
  if f then
    return f(str, idx)
  end
  decode_error(str, idx, "unexpected character '" .. chr .. "'")
end


function json.decode(str)
  if type(str) ~= "string" then
    error("expected argument of type string, got " .. type(str))
  end
  local res, idx = parse(str, next_char(str, 1, space_chars, true))
  idx = next_char(str, idx, space_chars, true)
  if idx <= #str then
    decode_error(str, idx, "trailing garbage")
  end
  return res
end


return json
t var IPV6_JOIN_GROUP* {.importc: "IPV6_JOIN_GROUP", header: "<sys/socket.h>".}: cint var IPV6_LEAVE_GROUP* {.importc: "IPV6_LEAVE_GROUP", header: "<sys/socket.h>".}: cint var IPV6_MULTICAST_HOPS* {.importc: "IPV6_MULTICAST_HOPS", header: "<sys/socket.h>".}: cint var IPV6_MULTICAST_IF* {.importc: "IPV6_MULTICAST_IF", header: "<sys/socket.h>".}: cint var IPV6_MULTICAST_LOOP* {.importc: "IPV6_MULTICAST_LOOP", header: "<sys/socket.h>".}: cint var IPV6_UNICAST_HOPS* {.importc: "IPV6_UNICAST_HOPS", header: "<sys/socket.h>".}: cint var IPV6_V6ONLY* {.importc: "IPV6_V6ONLY", header: "<sys/socket.h>".}: cint # <netinet/tcp.h> const TCP_NODELAY* = 0x01 # don't delay send to coalesce packets const TCP_KEEPALIVE* = 0x02 # send KEEPALIVE probes when idle for pcb->keep_idle milliseconds const TCP_KEEPIDLE* = 0x03 # set pcb->keep_idle - Same as TCP_KEEPALIVE, but use seconds for get/setsockopt const TCP_KEEPINTVL* = 0x04 # set pcb->keep_intvl - Use seconds for get/setsockopt const TCP_KEEPCNT* = 0x05 # set pcb->keep_cnt - Use number of probes sent for get/setsockopt # <nl_types.h> # var NL_SETD* {.importc: "NL_SETD", header: "<nl_types.h>".}: cint # var NL_CAT_LOCALE* {.importc: "NL_CAT_LOCALE", header: "<nl_types.h>".}: cint # <sys/poll.h> # var POLLIN* {.importc: "POLLIN", header: "<sys/poll.h>".}: cshort # var POLLRDNORM* {.importc: "POLLRDNORM", header: "<sys/poll.h>".}: cshort # var POLLRDBAND* {.importc: "POLLRDBAND", header: "<sys/poll.h>".}: cshort # var POLLPRI* {.importc: "POLLPRI", header: "<sys/poll.h>".}: cshort # var POLLOUT* {.importc: "POLLOUT", header: "<sys/poll.h>".}: cshort # var POLLWRNORM* {.importc: "POLLWRNORM", header: "<sys/poll.h>".}: cshort # var POLLWRBAND* {.importc: "POLLWRBAND", header: "<sys/poll.h>".}: cshort # var POLLERR* {.importc: "POLLERR", header: "<sys/poll.h>".}: cshort # var POLLHUP* {.importc: "POLLHUP", header: "<sys/poll.h>".}: cshort # var POLLNVAL* {.importc: "POLLNVAL", header: "<sys/poll.h>".}: cshort # <pthread.h> var PTHREAD_STACK_MIN* {.importc: "PTHREAD_STACK_MIN", header: "<pthread.h>".}: cint # var PTHREAD_BARRIER_SERIAL_THREAD* {.importc: "PTHREAD_BARRIER_SERIAL_THREAD", header: "<pthread.h>".}: cint # var PTHREAD_CANCEL_ASYNCHRONOUS* {.importc: "PTHREAD_CANCEL_ASYNCHRONOUS", header: "<pthread.h>".}: cint # var PTHREAD_CANCEL_ENABLE* {.importc: "PTHREAD_CANCEL_ENABLE", header: "<pthread.h>".}: cint # var PTHREAD_CANCEL_DEFERRED* {.importc: "PTHREAD_CANCEL_DEFERRED", header: "<pthread.h>".}: cint # var PTHREAD_CANCEL_DISABLE* {.importc: "PTHREAD_CANCEL_DISABLE", header: "<pthread.h>".}: cint # var PTHREAD_CREATE_DETACHED* {.importc: "PTHREAD_CREATE_DETACHED", header: "<pthread.h>".}: cint # var PTHREAD_CREATE_JOINABLE* {.importc: "PTHREAD_CREATE_JOINABLE", header: "<pthread.h>".}: cint # var PTHREAD_EXPLICIT_SCHED* {.importc: "PTHREAD_EXPLICIT_SCHED", header: "<pthread.h>".}: cint # var PTHREAD_INHERIT_SCHED* {.importc: "PTHREAD_INHERIT_SCHED", header: "<pthread.h>".}: cint # var PTHREAD_MUTEX_DEFAULT* {.importc: "PTHREAD_MUTEX_DEFAULT", header: "<pthread.h>".}: cint # var PTHREAD_MUTEX_ERRORCHECK* {.importc: "PTHREAD_MUTEX_ERRORCHECK", header: "<pthread.h>".}: cint # var PTHREAD_MUTEX_NORMAL* {.importc: "PTHREAD_MUTEX_NORMAL", header: "<pthread.h>".}: cint # var PTHREAD_MUTEX_RECURSIVE* {.importc: "PTHREAD_MUTEX_RECURSIVE", header: "<pthread.h>".}: cint # var PTHREAD_PRIO_INHERIT* {.importc: "PTHREAD_PRIO_INHERIT", header: "<pthread.h>".}: cint # var PTHREAD_PRIO_NONE* {.importc: "PTHREAD_PRIO_NONE", header: "<pthread.h>".}: cint # var PTHREAD_PRIO_PROTECT* {.importc: "PTHREAD_PRIO_PROTECT", header: "<pthread.h>".}: cint # var PTHREAD_PROCESS_SHARED* {.importc: "PTHREAD_PROCESS_SHARED", header: "<pthread.h>".}: cint # var PTHREAD_PROCESS_PRIVATE* {.importc: "PTHREAD_PROCESS_PRIVATE", header: "<pthread.h>".}: cint # var PTHREAD_SCOPE_PROCESS* {.importc: "PTHREAD_SCOPE_PROCESS", header: "<pthread.h>".}: cint # var PTHREAD_SCOPE_SYSTEM* {.importc: "PTHREAD_SCOPE_SYSTEM", header: "<pthread.h>".}: cint # # <sched.h> # var SCHED_FIFO* {.importc: "SCHED_FIFO", header: "<sched.h>".}: cint # var SCHED_RR* {.importc: "SCHED_RR", header: "<sched.h>".}: cint # var SCHED_SPORADIC* {.importc: "SCHED_SPORADIC", header: "<sched.h>".}: cint # var SCHED_OTHER* {.importc: "SCHED_OTHER", header: "<sched.h>".}: cint # <semaphore.h> var SEM_FAILED* {.importc: "SEM_FAILED", header: "<semaphore.h>".}: pointer # # <signal.h> # var SIGEV_NONE* {.importc: "SIGEV_NONE", header: "<signal.h>".}: cint # var SIGEV_SIGNAL* {.importc: "SIGEV_SIGNAL", header: "<signal.h>".}: cint # var SIGEV_THREAD* {.importc: "SIGEV_THREAD", header: "<signal.h>".}: cint # var SIGABRT* {.importc: "SIGABRT", header: "<signal.h>".}: cint # var SIGALRM* {.importc: "SIGALRM", header: "<signal.h>".}: cint # var SIGBUS* {.importc: "SIGBUS", header: "<signal.h>".}: cint # var SIGCHLD* {.importc: "SIGCHLD", header: "<signal.h>".}: cint # var SIGCONT* {.importc: "SIGCONT", header: "<signal.h>".}: cint # var SIGFPE* {.importc: "SIGFPE", header: "<signal.h>".}: cint # var SIGHUP* {.importc: "SIGHUP", header: "<signal.h>".}: cint # var SIGILL* {.importc: "SIGILL", header: "<signal.h>".}: cint # var SIGINT* {.importc: "SIGINT", header: "<signal.h>".}: cint # var SIGKILL* {.importc: "SIGKILL", header: "<signal.h>".}: cint # var SIGPIPE* {.importc: "SIGPIPE", header: "<signal.h>".}: cint # var SIGQUIT* {.importc: "SIGQUIT", header: "<signal.h>".}: cint # var SIGSEGV* {.importc: "SIGSEGV", header: "<signal.h>".}: cint # var SIGSTOP* {.importc: "SIGSTOP", header: "<signal.h>".}: cint # var SIGTERM* {.importc: "SIGTERM", header: "<signal.h>".}: cint # var SIGTSTP* {.importc: "SIGTSTP", header: "<signal.h>".}: cint # var SIGTTIN* {.importc: "SIGTTIN", header: "<signal.h>".}: cint # var SIGTTOU* {.importc: "SIGTTOU", header: "<signal.h>".}: cint # var SIGUSR1* {.importc: "SIGUSR1", header: "<signal.h>".}: cint # var SIGUSR2* {.importc: "SIGUSR2", header: "<signal.h>".}: cint # var SIGPOLL* {.importc: "SIGPOLL", header: "<signal.h>".}: cint # var SIGPROF* {.importc: "SIGPROF", header: "<signal.h>".}: cint # var SIGSYS* {.importc: "SIGSYS", header: "<signal.h>".}: cint # var SIGTRAP* {.importc: "SIGTRAP", header: "<signal.h>".}: cint # var SIGURG* {.importc: "SIGURG", header: "<signal.h>".}: cint # var SIGVTALRM* {.importc: "SIGVTALRM", header: "<signal.h>".}: cint # var SIGXCPU* {.importc: "SIGXCPU", header: "<signal.h>".}: cint # var SIGXFSZ* {.importc: "SIGXFSZ", header: "<signal.h>".}: cint # var SA_NOCLDSTOP* {.importc: "SA_NOCLDSTOP", header: "<signal.h>".}: cint # var SIG_BLOCK* {.importc: "SIG_BLOCK", header: "<signal.h>".}: cint # var SIG_UNBLOCK* {.importc: "SIG_UNBLOCK", header: "<signal.h>".}: cint # var SIG_SETMASK* {.importc: "SIG_SETMASK", header: "<signal.h>".}: cint # var SA_ONSTACK* {.importc: "SA_ONSTACK", header: "<signal.h>".}: cint # var SA_RESETHAND* {.importc: "SA_RESETHAND", header: "<signal.h>".}: cint # var SA_RESTART* {.importc: "SA_RESTART", header: "<signal.h>".}: cint # var SA_SIGINFO* {.importc: "SA_SIGINFO", header: "<signal.h>".}: cint # var SA_NOCLDWAIT* {.importc: "SA_NOCLDWAIT", header: "<signal.h>".}: cint # var SA_NODEFER* {.importc: "SA_NODEFER", header: "<signal.h>".}: cint # var SS_ONSTACK* {.importc: "SS_ONSTACK", header: "<signal.h>".}: cint # var SS_DISABLE* {.importc: "SS_DISABLE", header: "<signal.h>".}: cint # var MINSIGSTKSZ* {.importc: "MINSIGSTKSZ", header: "<signal.h>".}: cint # var SIGSTKSZ* {.importc: "SIGSTKSZ", header: "<signal.h>".}: cint # var SIG_HOLD* {.importc: "SIG_HOLD", header: "<signal.h>".}: Sighandler # var SIG_DFL* {.importc: "SIG_DFL", header: "<signal.h>".}: Sighandler # var SIG_ERR* {.importc: "SIG_ERR", header: "<signal.h>".}: Sighandler # var SIG_IGN* {.importc: "SIG_IGN", header: "<signal.h>".}: Sighandler # # <sys/ipc.h> # var IPC_CREAT* {.importc: "IPC_CREAT", header: "<sys/ipc.h>".}: cint # var IPC_EXCL* {.importc: "IPC_EXCL", header: "<sys/ipc.h>".}: cint # var IPC_NOWAIT* {.importc: "IPC_NOWAIT", header: "<sys/ipc.h>".}: cint # var IPC_PRIVATE* {.importc: "IPC_PRIVATE", header: "<sys/ipc.h>".}: cint # var IPC_RMID* {.importc: "IPC_RMID", header: "<sys/ipc.h>".}: cint # var IPC_SET* {.importc: "IPC_SET", header: "<sys/ipc.h>".}: cint # var IPC_STAT* {.importc: "IPC_STAT", header: "<sys/ipc.h>".}: cint # # <sys/mman.h> # var PROT_READ* {.importc: "PROT_READ", header: "<sys/mman.h>".}: cint # var PROT_WRITE* {.importc: "PROT_WRITE", header: "<sys/mman.h>".}: cint # var PROT_EXEC* {.importc: "PROT_EXEC", header: "<sys/mman.h>".}: cint # var PROT_NONE* {.importc: "PROT_NONE", header: "<sys/mman.h>".}: cint # var MAP_ANONYMOUS* {.importc: "MAP_ANONYMOUS", header: "<sys/mman.h>".}: cint # var MAP_FIXED_NOREPLACE* {.importc: "MAP_FIXED_NOREPLACE", header: "<sys/mman.h>".}: cint # var MAP_NORESERVE* {.importc: "MAP_NORESERVE", header: "<sys/mman.h>".}: cint # var MAP_SHARED* {.importc: "MAP_SHARED", header: "<sys/mman.h>".}: cint # var MAP_PRIVATE* {.importc: "MAP_PRIVATE", header: "<sys/mman.h>".}: cint # var MAP_FIXED* {.importc: "MAP_FIXED", header: "<sys/mman.h>".}: cint # var MS_ASYNC* {.importc: "MS_ASYNC", header: "<sys/mman.h>".}: cint # var MS_SYNC* {.importc: "MS_SYNC", header: "<sys/mman.h>".}: cint # var MS_INVALIDATE* {.importc: "MS_INVALIDATE", header: "<sys/mman.h>".}: cint # var MCL_CURRENT* {.importc: "MCL_CURRENT", header: "<sys/mman.h>".}: cint # var MCL_FUTURE* {.importc: "MCL_FUTURE", header: "<sys/mman.h>".}: cint # var MAP_FAILED* {.importc: "MAP_FAILED", header: "<sys/mman.h>".}: pointer # var POSIX_MADV_NORMAL* {.importc: "POSIX_MADV_NORMAL", header: "<sys/mman.h>".}: cint # var POSIX_MADV_SEQUENTIAL* {.importc: "POSIX_MADV_SEQUENTIAL", header: "<sys/mman.h>".}: cint # var POSIX_MADV_RANDOM* {.importc: "POSIX_MADV_RANDOM", header: "<sys/mman.h>".}: cint # var POSIX_MADV_WILLNEED* {.importc: "POSIX_MADV_WILLNEED", header: "<sys/mman.h>".}: cint # var POSIX_MADV_DONTNEED* {.importc: "POSIX_MADV_DONTNEED", header: "<sys/mman.h>".}: cint # var POSIX_TYPED_MEM_ALLOCATE* {.importc: "POSIX_TYPED_MEM_ALLOCATE", header: "<sys/mman.h>".}: cint # var POSIX_TYPED_MEM_ALLOCATE_CONTIG* {.importc: "POSIX_TYPED_MEM_ALLOCATE_CONTIG", header: "<sys/mman.h>".}: cint # var POSIX_TYPED_MEM_MAP_ALLOCATABLE* {.importc: "POSIX_TYPED_MEM_MAP_ALLOCATABLE", header: "<sys/mman.h>".}: cint # <sys/resource.h> # var RLIMIT_NOFILE* {.importc: "RLIMIT_NOFILE", header: "<sys/resource.h>".}: cint # <sys/select.h> var FD_SETSIZE* {.importc: "FD_SETSIZE", header: "<sys/select.h>".}: cint # <sys/socket.h> # struct msghdr->msg_flags bit field values const MSG_TRUNC* = 0x04 const MSG_CTRUNC* = 0x08 # Flags we can use with send and recv. const MSG_PEEK* = 0x01 # Peeks at an incoming message const MSG_WAITALL* = 0x02 # Unimplemented: Requests that the function block until the full amount of data requested can be returned const MSG_OOB* = 0x04 # Unimplemented: Requests out-of-band data. The significance and semantics of out-of-band data are protocol-specific const MSG_DONTWAIT* = 0x08 # Nonblocking i/o for this operation only const MSG_MORE* = 0x10 # Sender will send more # const MSG_NOSIGNAL* = 0x20 # Uninmplemented: Requests not to send the SIGPIPE signal if an attempt to send is made on a stream-oriented socket that is no longer connected. # Alternately, they can defined like this, but the above seems better when they're known/stable values: # var MSG_TRUNC* {.importc: "MSG_TRUNC", header: "<sys/socket.h>".}: cint # var MSG_CTRUNC* {.importc: "MSG_CTRUNC", header: "<sys/socket.h>".}: cint # var MSG_DONTROUTE* {.importc: "MSG_DONTROUTE", header: "<sys/socket.h>".}: cint # not defined in lwip # var MSG_EOR* {.importc: "MSG_EOR", header: "<sys/socket.h>".}: cint # not defined in lwip # var MSG_OOB* {.importc: "MSG_OOB", header: "<sys/socket.h>".}: cint # var SCM_RIGHTS* {.importc: "SCM_RIGHTS", header: "<sys/socket.h>".}: cint var SO_ACCEPTCONN* {.importc: "SO_ACCEPTCONN", header: "<sys/socket.h>".}: cint var SO_BROADCAST* {.importc: "SO_BROADCAST", header: "<sys/socket.h>".}: cint var SO_DEBUG* {.importc: "SO_DEBUG", header: "<sys/socket.h>".}: cint var SO_DONTROUTE* {.importc: "SO_DONTROUTE", header: "<sys/socket.h>".}: cint var SO_ERROR* {.importc: "SO_ERROR", header: "<sys/socket.h>".}: cint var SO_KEEPALIVE* {.importc: "SO_KEEPALIVE", header: "<sys/socket.h>".}: cint var SO_LINGER* {.importc: "SO_LINGER", header: "<sys/socket.h>".}: cint var SO_OOBINLINE* {.importc: "SO_OOBINLINE", header: "<sys/socket.h>".}: cint var SO_RCVBUF* {.importc: "SO_RCVBUF", header: "<sys/socket.h>".}: cint var SO_RCVLOWAT* {.importc: "SO_RCVLOWAT", header: "<sys/socket.h>".}: cint var SO_RCVTIMEO* {.importc: "SO_RCVTIMEO", header: "<sys/socket.h>".}: cint var SO_REUSEADDR* {.importc: "SO_REUSEADDR", header: "<sys/socket.h>".}: cint var SO_SNDBUF* {.importc: "SO_SNDBUF", header: "<sys/socket.h>".}: cint var SO_SNDLOWAT* {.importc: "SO_SNDLOWAT", header: "<sys/socket.h>".}: cint var SO_SNDTIMEO* {.importc: "SO_SNDTIMEO", header: "<sys/socket.h>".}: cint var SO_TYPE* {.importc: "SO_TYPE", header: "<sys/socket.h>".}: cint var SOCK_DGRAM* {.importc: "SOCK_DGRAM", header: "<sys/socket.h>".}: cint var SOCK_RAW* {.importc: "SOCK_RAW", header: "<sys/socket.h>".}: cint # var SOCK_SEQPACKET* {.importc: "SOCK_SEQPACKET", header: "<sys/socket.h>".}: cint const SOCK_SEQPACKET* = cint(5) var SOCK_STREAM* {.importc: "SOCK_STREAM", header: "<sys/socket.h>".}: cint var SOL_SOCKET* {.importc: "SOL_SOCKET", header: "<sys/socket.h>".}: cint const SocketMaxConnections {.intdefine.}: int = 32 var SOMAXCONN*: cint = SocketMaxConnections.cint var AF_INET* {.importc: "AF_INET", header: "<sys/socket.h>".}: cint var AF_INET6* {.importc: "AF_INET6", header: "<sys/socket.h>".}: cint # var AF_UNIX* {.importc: "AF_UNIX", header: "<sys/socket.h>".}: cint const AF_UNIX*: cint = 1 # for compat with Nim libraries, doesn't exist on freertos var AF_UNSPEC* {.importc: "AF_UNSPEC", header: "<sys/socket.h>".}: cint var SHUT_RD* {.importc: "SHUT_RD", header: "<sys/socket.h>".}: cint var SHUT_RDWR* {.importc: "SHUT_RDWR", header: "<sys/socket.h>".}: cint var SHUT_WR* {.importc: "SHUT_WR", header: "<sys/socket.h>".}: cint # # <sys/stat.h> # <sys/stat.h> # var S_IFBLK* {.importc: "S_IFBLK", header: "<sys/stat.h>".}: cint # var S_IFCHR* {.importc: "S_IFCHR", header: "<sys/stat.h>".}: cint # var S_IFDIR* {.importc: "S_IFDIR", header: "<sys/stat.h>".}: cint # var S_IFIFO* {.importc: "S_IFIFO", header: "<sys/stat.h>".}: cint # var S_IFLNK* {.importc: "S_IFLNK", header: "<sys/stat.h>".}: cint # var S_IFMT* {.importc: "S_IFMT", header: "<sys/stat.h>".}: cint # var S_IFREG* {.importc: "S_IFREG", header: "<sys/stat.h>".}: cint # var S_IFSOCK* {.importc: "S_IFSOCK", header: "<sys/stat.h>".}: cint var S_IRGRP* {.importc: "S_IRGRP", header: "<sys/stat.h>".}: cint var S_IROTH* {.importc: "S_IROTH", header: "<sys/stat.h>".}: cint var S_IRUSR* {.importc: "S_IRUSR", header: "<sys/stat.h>".}: cint # var S_IRWXG* {.importc: "S_IRWXG", header: "<sys/stat.h>".}: cint # var S_IRWXO* {.importc: "S_IRWXO", header: "<sys/stat.h>".}: cint # var S_IRWXU* {.importc: "S_IRWXU", header: "<sys/stat.h>".}: cint # var S_ISGID* {.importc: "S_ISGID", header: "<sys/stat.h>".}: cint # var S_ISUID* {.importc: "S_ISUID", header: "<sys/stat.h>".}: cint # var S_ISVTX* {.importc: "S_ISVTX", header: "<sys/stat.h>".}: cint var S_IWGRP* {.importc: "S_IWGRP", header: "<sys/stat.h>".}: cint var S_IWOTH* {.importc: "S_IWOTH", header: "<sys/stat.h>".}: cint var S_IWUSR* {.importc: "S_IWUSR", header: "<sys/stat.h>".}: cint var S_IXGRP* {.importc: "S_IXGRP", header: "<sys/stat.h>".}: cint var S_IXOTH* {.importc: "S_IXOTH", header: "<sys/stat.h>".}: cint var S_IXUSR* {.importc: "S_IXUSR", header: "<sys/stat.h>".}: cint # # <sys/statvfs.h> # var ST_RDONLY* {.importc: "ST_RDONLY", header: "<sys/statvfs.h>".}: cint # var ST_NOSUID* {.importc: "ST_NOSUID", header: "<sys/statvfs.h>".}: cint # # <sys/wait.h> # var WNOHANG* {.importc: "WNOHANG", header: "<sys/wait.h>".}: cint # var WUNTRACED* {.importc: "WUNTRACED", header: "<sys/wait.h>".}: cint # var WEXITED* {.importc: "WEXITED", header: "<sys/wait.h>".}: cint # var WSTOPPED* {.importc: "WSTOPPED", header: "<sys/wait.h>".}: cint # var WCONTINUED* {.importc: "WCONTINUED", header: "<sys/wait.h>".}: cint # var WNOWAIT* {.importc: "WNOWAIT", header: "<sys/wait.h>".}: cint # var P_ALL* {.importc: "P_ALL", header: "<sys/wait.h>".}: cint # var P_PID* {.importc: "P_PID", header: "<sys/wait.h>".}: cint # var P_PGID* {.importc: "P_PGID", header: "<sys/wait.h>".}: cint # # <spawn.h> # var POSIX_SPAWN_RESETIDS* {.importc: "POSIX_SPAWN_RESETIDS", header: "<spawn.h>".}: cint # var POSIX_SPAWN_SETPGROUP* {.importc: "POSIX_SPAWN_SETPGROUP", header: "<spawn.h>".}: cint # var POSIX_SPAWN_SETSCHEDPARAM* {.importc: "POSIX_SPAWN_SETSCHEDPARAM", header: "<spawn.h>".}: cint # var POSIX_SPAWN_SETSCHEDULER* {.importc: "POSIX_SPAWN_SETSCHEDULER", header: "<spawn.h>".}: cint # var POSIX_SPAWN_SETSIGDEF* {.importc: "POSIX_SPAWN_SETSIGDEF", header: "<spawn.h>".}: cint # var POSIX_SPAWN_SETSIGMASK* {.importc: "POSIX_SPAWN_SETSIGMASK", header: "<spawn.h>".}: cint ## <stdio.h> # var IOFBF* {.importc: "_IOFBF", header: "<stdio.h>".}: cint # var IONBF* {.importc: "_IONBF", header: "<stdio.h>".}: cint # <time.h> var CLOCKS_PER_SEC* {.importc: "CLOCKS_PER_SEC", header: "<time.h>".}: clong var CLOCK_PROCESS_CPUTIME_ID* {.importc: "CLOCK_PROCESS_CPUTIME_ID", header: "<time.h>".}: cint var CLOCK_THREAD_CPUTIME_ID* {.importc: "CLOCK_THREAD_CPUTIME_ID", header: "<time.h>".}: cint var CLOCK_REALTIME* {.importc: "CLOCK_REALTIME", header: "<time.h>".}: cint var TIMER_ABSTIME* {.importc: "TIMER_ABSTIME", header: "<time.h>".}: cint var CLOCK_MONOTONIC* {.importc: "CLOCK_MONOTONIC", header: "<time.h>".}: cint # <unistd.h> const F_OK* = cint(0) const R_OK* = cint(4) const W_OK* = cint(2) const X_OK* = cint(1) const F_LOCK* = cint(1) const F_TEST* = cint(3) const F_TLOCK* = cint(2) const F_ULOCK* = cint(0)