tinyirc.lua 2.6 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889
  1. -----------------------------------------------------------------------------
  2. -- Select sample: simple text line server
  3. -- LuaSocket sample files.
  4. -- Author: Diego Nehab
  5. -----------------------------------------------------------------------------
  6. local socket = require("socket")
  7. host = host or "*"
  8. port1 = port1 or 8080
  9. port2 = port2 or 8181
  10. if arg then
  11. host = arg[1] or host
  12. port1 = arg[2] or port1
  13. port2 = arg[3] or port2
  14. end
  15. server1 = assert(socket.bind(host, port1))
  16. server2 = assert(socket.bind(host, port2))
  17. server1:settimeout(1) -- make sure we don't block in accept
  18. server2:settimeout(1)
  19. io.write("Servers bound\n")
  20. -- simple set implementation
  21. -- the select function doesn't care about what is passed to it as long as
  22. -- it behaves like a table
  23. -- creates a new set data structure
  24. function newset()
  25. local reverse = {}
  26. local set = {}
  27. return setmetatable(set, {__index = {
  28. insert = function(set, value)
  29. if not reverse[value] then
  30. table.insert(set, value)
  31. reverse[value] = #set
  32. end
  33. end,
  34. remove = function(set, value)
  35. local index = reverse[value]
  36. if index then
  37. reverse[value] = nil
  38. local top = table.remove(set)
  39. if top ~= value then
  40. reverse[top] = index
  41. set[index] = top
  42. end
  43. end
  44. end
  45. }})
  46. end
  47. set = newset()
  48. io.write("Inserting servers in set\n")
  49. set:insert(server1)
  50. set:insert(server2)
  51. while 1 do
  52. local readable, _, error = socket.select(set, nil)
  53. for _, input in ipairs(readable) do
  54. -- is it a server socket?
  55. if input == server1 or input == server2 then
  56. io.write("Waiting for clients\n")
  57. local new = input:accept()
  58. if new then
  59. new:settimeout(1)
  60. io.write("Inserting client in set\n")
  61. set:insert(new)
  62. end
  63. -- it is a client socket
  64. else
  65. local line, error = input:receive()
  66. if error then
  67. input:close()
  68. io.write("Removing client from set\n")
  69. set:remove(input)
  70. else
  71. io.write("Broadcasting line '", line, "'\n")
  72. writable, error = socket.skip(1, socket.select(nil, set, 1))
  73. if not error then
  74. for __, output in ipairs(writable) do
  75. if output ~= input then
  76. output:send(line .. "\n")
  77. end
  78. end
  79. else io.write("No client ready to receive!!!\n") end
  80. end
  81. end
  82. end
  83. end