-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathinit.lua
More file actions
84 lines (74 loc) · 2.4 KB
/
init.lua
File metadata and controls
84 lines (74 loc) · 2.4 KB
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
-- allay-server: serve allay packages over rednet.
--
-- Run on a CC computer with a wireless modem. Other computers can then
-- `allay source add rednet://<this-station>` and install packages from
-- this host.
--
-- Files served from a configurable directory (default /home/allay-source/).
local PROTOCOL = "allay-source"
local DEFAULT_DIR = "/home/allay-source"
local STATION = os.getComputerLabel() or ("allay-" .. os.getComputerID())
local function find_modem()
for _, side in ipairs(peripheral.getNames()) do
if peripheral.getType(side) == "modem"
and peripheral.call(side, "isWireless") then
return side
end
end
return nil
end
local function read_file(path)
if not fs.exists(path) then return nil, "not found: " .. path end
local f = fs.open(path, "r")
if not f then return nil, "cannot open: " .. path end
local content = f.readAll()
f.close()
return content
end
local function safe_path(root, requested)
-- Reject paths with .. or null bytes.
if requested:find("%.%.") or requested:find("\0") then
return nil
end
if requested:sub(1, 1) == "/" then requested = requested:sub(2) end
return root .. "/" .. requested
end
local function main(argv)
argv = argv or {}
local root = argv[1] or DEFAULT_DIR
if not fs.exists(root) then
print("error: source directory does not exist: " .. root)
print("usage: allay-server <directory>")
return
end
local side = find_modem()
if not side then
print("error: no wireless modem attached")
return
end
rednet.open(side)
rednet.host(PROTOCOL, STATION)
print(string.format("allay-server serving %s as rednet station '%s'", root, STATION))
print("(press Ctrl+T to stop)")
while true do
local sender, msg = rednet.receive(PROTOCOL)
if type(msg) == "table" and type(msg.action) == "string" then
if msg.action == "get" and type(msg.path) == "string" then
local full = safe_path(root, msg.path)
if not full then
rednet.send(sender, { ok = false, err = "invalid path" }, PROTOCOL)
else
local content, err = read_file(full)
if content then
rednet.send(sender, { ok = true, content = content }, PROTOCOL)
else
rednet.send(sender, { ok = false, err = err }, PROTOCOL)
end
end
else
rednet.send(sender, { ok = false, err = "unknown action" }, PROTOCOL)
end
end
end
end
main({...})