aboutsummaryrefslogtreecommitdiff
path: root/test
diff options
context:
space:
mode:
authormoteus <mimir@newmail.ru>2013-12-26 12:00:41 +0400
committermoteus <mimir@newmail.ru>2013-12-26 12:00:41 +0400
commitfebf9da1af8ba4cf0f8cc64b6af2adb0dcf9b354 (patch)
tree735ef634f8ebeab2101aa21897fd4e4e2f826f32 /test
parent46ed59584e5407c49a02f1ea6bede6487259a92e (diff)
downloadlua-llthreads2-febf9da1af8ba4cf0f8cc64b6af2adb0dcf9b354.tar.gz
lua-llthreads2-febf9da1af8ba4cf0f8cc64b6af2adb0dcf9b354.tar.bz2
lua-llthreads2-febf9da1af8ba4cf0f8cc64b6af2adb0dcf9b354.zip
First commit.
Diffstat (limited to 'test')
-rw-r--r--test/test_llthreads.lua80
-rw-r--r--test/test_table_copy.lua134
-rw-r--r--test/test_threads.lua74
3 files changed, 288 insertions, 0 deletions
diff --git a/test/test_llthreads.lua b/test/test_llthreads.lua
new file mode 100644
index 0000000..3474b9b
--- /dev/null
+++ b/test/test_llthreads.lua
@@ -0,0 +1,80 @@
1-- Copyright (c) 2011 by Robert G. Jakabosky <bobby@sharedrealm.com>
2--
3-- Permission is hereby granted, free of charge, to any person obtaining a copy
4-- of this software and associated documentation files (the "Software"), to deal
5-- in the Software without restriction, including without limitation the rights
6-- to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
7-- copies of the Software, and to permit persons to whom the Software is
8-- furnished to do so, subject to the following conditions:
9--
10-- The above copyright notice and this permission notice shall be included in
11-- all copies or substantial portions of the Software.
12--
13-- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
14-- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
15-- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
16-- AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
17-- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
18-- OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
19-- THE SOFTWARE.
20
21local llthreads = require"llthreads"
22
23local sleep
24local status, socket = pcall(require,"socket")
25if status then
26 sleep = function(secs)
27 return socket.sleep(secs)
28 end
29end
30
31if not sleep then
32 local status, ztimer = pcall(require, "lzmq.timer")
33 if status then
34 sleep = function(secs)
35 ztimer.sleep(secs * 1000)
36 end
37 end
38end
39
40if not sleep then
41 sleep = function(secs)
42 os.execute("sleep " .. tonumber(secs))
43 end
44end
45
46local function detached_thread(...)
47 local thread = llthreads.new([[ print("print_detached_thread:", ...) ]], ...)
48 -- start detached thread
49 assert(thread:start(true))
50 return thread
51end
52
53local function print_thread(...)
54 local thread = llthreads.new([[ print("print_thread:", ...); ]], ...)
55 -- start joinable thread
56 assert(thread:start())
57 return thread
58end
59
60local function pass_through_thread(...)
61 local thread = llthreads.new([[ return "pass_thread:", ... ]], ...)
62 -- start joinable thread
63 assert(thread:start())
64 return thread
65end
66
67local thread1 = detached_thread("number:", 1234, "nil:", nil, "bool:", true)
68
69sleep(1)
70
71local thread2 = print_thread("number:", 1234, "nil:", nil, "bool:", true)
72print("thread2:join: results # = ", select('#', thread2:join()))
73
74sleep(1)
75
76local thread3 = pass_through_thread("number:", 1234, "nil:", nil, "bool:", true)
77print("thread3:join:", thread3:join())
78
79sleep(1)
80
diff --git a/test/test_table_copy.lua b/test/test_table_copy.lua
new file mode 100644
index 0000000..0408ad3
--- /dev/null
+++ b/test/test_table_copy.lua
@@ -0,0 +1,134 @@
1-- Copyright (c) 2011 by Robert G. Jakabosky <bobby@sharedrealm.com>
2--
3-- Permission is hereby granted, free of charge, to any person obtaining a copy
4-- of this software and associated documentation files (the "Software"), to deal
5-- in the Software without restriction, including without limitation the rights
6-- to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
7-- copies of the Software, and to permit persons to whom the Software is
8-- furnished to do so, subject to the following conditions:
9--
10-- The above copyright notice and this permission notice shall be included in
11-- all copies or substantial portions of the Software.
12--
13-- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
14-- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
15-- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
16-- AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
17-- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
18-- OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
19-- THE SOFTWARE.
20
21local llthreads = require"llthreads"
22
23local sleep
24local status, socket = pcall(require,"socket")
25if status then
26 sleep = function(secs)
27 return socket.sleep(secs)
28 end
29else
30 sleep = function(secs)
31 os.execute("sleep " .. tonumber(secs))
32 end
33end
34
35local dump_code = [==[
36local function dump_recur(seen, obj, depth)
37 local out
38 local t = type(obj)
39 -- if not a table just convert to string.
40 if t ~= "table" then
41 if t == "string" then
42 return '"' .. obj .. '"'
43 end
44 return tostring(obj)
45 end
46 -- check if this table has been seen already.
47 if seen[obj] then
48 return "Already dumped " .. tostring(obj)
49 end
50 seen[obj] = true
51 -- restrict max depth.
52 if depth >= 10 then
53 return "{... max depth reached ...}"
54 end
55 depth = depth + 1
56 -- output table key/value pairs
57 local tabs = string.rep(" ",depth)
58 local out = "{\n"
59 for k,v in pairs(obj) do
60 if type(k) ~= "number" then
61 out = out .. tabs .. '[' .. dump_recur(seen, k, depth) .. '] = ' ..
62 dump_recur(seen, v, depth) .. ',\n'
63 else
64 out = out .. tabs .. '[' .. k .. '] = ' .. dump_recur(seen, v, depth) .. ',\n'
65 end
66 end
67 return out .. tabs:sub(1,-3) .. "}"
68end
69
70local obj = ...
71local seen = {}
72return dump_recur(seen, obj, 0)
73]==]
74
75local dump = (loadstring or load)(dump_code)
76
77local child_code = [==[
78local dump = (loadstring or load)[[
79]==] .. dump_code .. [==[
80]]
81local args = ...
82
83print("Child thread args:", dump(args))
84
85-- return all values.
86return ...
87]==]
88
89local function test_thread_value_copying(...)
90 local args = {...}
91 print("Main thread args:", dump(args))
92 local thread = llthreads.new(child_code, args)
93 -- start joinable thread
94 assert(thread:start())
95
96 local status, results = thread:join()
97 print("Main thread results:", dump(results))
98end
99
100-- create some tables.
101local a1 = { "a1" }
102local a2 = { "a2" }
103local a3 = { "a3" }
104local a4 = { "a4" }
105local b1 = { a1, a2, a3, a4 }
106local b2 = { a1=a1, a2=a2, a3=a3, a4=a4 }
107
108--
109-- no loops
110--
111test_thread_value_copying(b1, b2)
112
113local top = {}
114-- self reference.
115top.top = top
116top[top] = top
117-- nested reference.
118top.sub1 = { sub2 = { sub3 = { top } } }
119
120--
121-- loops
122--
123test_thread_value_copying(top)
124
125--
126-- Test max depth
127--
128local outer = {}
129for n=1,100 do
130 outer = {outer}
131end
132local status, err = pcall(test_thread_value_copying,outer)
133assert(not status, "Assertion failed: max depth test failed.")
134
diff --git a/test/test_threads.lua b/test/test_threads.lua
new file mode 100644
index 0000000..467526e
--- /dev/null
+++ b/test/test_threads.lua
@@ -0,0 +1,74 @@
1-- Copyright (c) 2011 by Ross Anderson <ross_j_anderson@yahoo.com>
2--
3-- Permission is hereby granted, free of charge, to any person obtaining a copy
4-- of this software and associated documentation files (the "Software"), to deal
5-- in the Software without restriction, including without limitation the rights
6-- to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
7-- copies of the Software, and to permit persons to whom the Software is
8-- furnished to do so, subject to the following conditions:
9--
10-- The above copyright notice and this permission notice shall be included in
11-- all copies or substantial portions of the Software.
12--
13-- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
14-- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
15-- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
16-- AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
17-- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
18-- OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
19-- THE SOFTWARE.
20
21-- Sub-thread processing example in Lua using llthreads - 1,000 quick sub-thread execution
22
23-- luajit sub_threads.lua
24
25local llthreads = require"llthreads"
26
27local num_threads = tonumber(arg[1] or 1000)
28
29-- level 0 string literal enclosure [[ ]] of child execution code
30local thread_code = [[
31 local lua_init = os.getenv("lua_init")
32 if lua_init and #lua_init > 0 then
33 if lua_init:sub(1,1) == '@' then
34 dofile(lua_init:sub(2))
35 else
36 assert((loadstring or load)(lua_init))()
37 end
38 end
39
40 local num_threads = ...
41 print("CHILD: received from ROOT params:", ...)
42 local llthreads = require"llthreads" -- need to re-declare this under this scope
43 local t = {} -- thread storage table
44
45 -- create a new child sub-thread execution code - it requires level 1 literal string [=[ ]=] enclosures, level 2 would be [==[ ]==]
46 local executed_child_code = [=[
47 return "Hello from child sub-thread, new input params:", ...
48 ]=]
49
50 -- create 1000 sub-threads - which creates an incremental 30% / 20% utilization spike on the two AMD cpu cores
51 print("CHILD: Create sub threads:", num_threads)
52 for i=1,num_threads do
53 -- create child sub-thread with code to execute and the input parmeters
54 local thread = llthreads.new(executed_child_code , "number:", 1000 + i, "nil:", nil, "bool:", true)
55 assert(thread:start()) -- start new child sub-thread
56 table.insert(t, thread) -- append the thread at the end of the thread table
57 end
58
59 -- wait (block) for all child sub-threads to complete before returning to ROOT
60 while true do
61 -- always wait on the first element, since order is not important
62 print("CHILD: sub-thread returned: ", t[1]:join())
63 table.remove(t,1) -- always remove the first element
64 if (#t == 0) then break end
65 end
66 return ... -- return the parents' input params back to the root
67]]
68
69-- create child thread.
70local thread = llthreads.new(thread_code, num_threads, "number:", 1000, "nil:", nil, "bool:", true)
71-- start joinable child thread.
72assert(thread:start())
73-- wait for all child and child sub-threads to finish
74print("ROOT: child returned: ", thread:join())