dropfile.go 7.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228
  1. package door
  2. import (
  3. "bufio"
  4. "log"
  5. "os"
  6. "path"
  7. "strconv"
  8. "strings"
  9. "time"
  10. )
  11. /*
  12. https://github.com/NuSkooler/ansi-bbs/blob/master/docs/dropfile_formats/door32_sys.txt
  13. door32.sys:
  14. 0 Line 1 : Comm type (0=local, 1=serial, 2=telnet)
  15. 0 Line 2 : Comm or socket handle
  16. 38400 Line 3 : Baud rate
  17. Mystic 1.07 Line 4 : BBSID (software name and version)
  18. 1 Line 5 : User record position (1-based)
  19. James Coyle Line 6 : User's real name
  20. g00r00 Line 7 : User's handle/alias
  21. 255 Line 8 : User's security level
  22. 58 Line 9 : User's time left (in minutes)
  23. 1 Line 10: Emulation *(See below)
  24. 1 Line 11: Current node number
  25. Emulation:
  26. 0 = Ascii
  27. 1 = Ansi
  28. 2 = Avatar
  29. 3 = RIP
  30. 4 = Max Graphics
  31. http://wiki.synchro.net/ref:door.sys
  32. door.sys:
  33. Line # Example Description Comment
  34. 1 COM1: Comm Port COM0: = LOCAL MODE
  35. 2 2400 Baud (DCE) Rate 300 to 38400
  36. 3 8 Parity 7 or 8
  37. 4 1 Node Number 1 to 99
  38. 5 19200 DTE Rate Was Y/N (LOCKED at 19200)
  39. 6 Y Screen Display Y=On N=Off
  40. 7 Y Printer Toggle Y=On N=Off
  41. 8 Y Page Bell Y=On N=Off
  42. 9 Y Caller Alarm Y=On N=Off
  43. 10 Rick Greer User Full Name
  44. 11 Lewisville, Tx. Calling From
  45. 12 214 221-7814 Home Phone
  46. 13 214 221-7814 Work/Data Phone
  47. 14 PASSWORD Password
  48. 15 110 Security Level
  49. 16 1456 Total Times On 0 through 32767
  50. 17 03/14/88 Last Date Called mm/dd/yy
  51. 18 7560 Seconds Remaining THIS call
  52. 19 126 Minutes Remaining THIS call
  53. 20 GR Graphics Mode GR=Graph, NG=Non-Graph, 7E=7,E Caller
  54. 21 23 Page Length rows of text
  55. 22 Y User Mode Y = Expert, N = Novice
  56. 23 1234567 Conferences/Forums Registered In ABCDEFG
  57. 24 7 Conference Exited To DOOR From G
  58. 25 01/01/99 User Expiration Date mm/dd/yy
  59. 26 1 User File's Record Number 1+
  60. 27 Y Default Protocol X, C, Y, G, I, N, Etc.
  61. 28 0 Total Uploads
  62. 29 0 Total Downloads
  63. 30 0 Daily Download “K” Total
  64. 31 999999 Daily Download Max. “K” Limit
  65. 32 10/22/88 Caller's Birthdate mm/dd/yy
  66. 33 G:\GAP\MAIN Path to the MAIN directory where user file is
  67. 34 G:\GAP\GEN Path to the GEN directory
  68. 35 Michael Sysop's Name name BBS refers to Sysop as
  69. 36 Stud Alias name user's alias or handle
  70. 37 00:05 Event time hh:mm
  71. 38 Y Error correcting connection Y/N
  72. 39 N ANSI supported & caller using NG mode Y/N
  73. 40 Y Use Record Locking Y/N
  74. 41 14 BBS Default Color CGA color code (1-15)
  75. 42 10 Time Credits in Minutes -32768 through 32767
  76. 43 07/07/90 Last New File Scan Date mm/dd/yy
  77. 44 14:32 Time of This Call hh:mm
  78. 45 07:30 Time of Last Call hh:mm
  79. 46 6 Maximum daily files available
  80. 47 3 Files d/led so far today
  81. 48 23456 Total “K” Bytes Uploaded
  82. 49 76329 Total “K” Bytes Downloaded
  83. 50 A File Sucker User Comment
  84. 51 10 Total Doors Opened
  85. 52 10283 Total Messages Left 0 through 32767
  86. */
  87. // DropFile Information
  88. type DropfileConfig struct {
  89. Comm_type int // Comm type (0 local, 2 telnet "linux fd")
  90. Comm_handle int // Handle to use to talk to the user
  91. BBSID string // BBS Software name
  92. User_number int // User number
  93. Real_name string // User's Real Name
  94. Handle string // User's Handle/Nick
  95. Security_level int // Security Level (if given)
  96. Time_left int // Time Left (minutes)
  97. Node int // BBS Node number
  98. }
  99. // Read the BBS door file. We only support door32.sys.
  100. func (d *Door) ReadDropfile(filename string) {
  101. var file *os.File
  102. var err error
  103. var base string = strings.ToLower(path.Base(filename))
  104. var isDoor32, isDoorSys bool
  105. if strings.Contains(base, "door.sys") {
  106. isDoorSys = true
  107. } else if strings.Contains(base, "door32.sys") {
  108. isDoor32 = true
  109. } else {
  110. log.Panicf("Unknown dropfile format: %s\n", base)
  111. }
  112. file, err = os.Open(filename)
  113. if err != nil {
  114. log.Panicf("Open(%s): %s\n", filename, err)
  115. }
  116. defer file.Close()
  117. var lines []string
  118. // read line by line
  119. // The scanner handles DOS and linux file endings.
  120. var scanner *bufio.Scanner = bufio.NewScanner(file)
  121. for scanner.Scan() {
  122. line := scanner.Text()
  123. lines = append(lines, line)
  124. }
  125. if isDoor32 {
  126. // door32.sys:
  127. // 0 Line 1 : Comm type (0=local, 1=serial, 2=telnet)
  128. // 0 Line 2 : Comm or socket handle
  129. // Mystic 1.07 Line 4 : BBSID (software name and version)
  130. // 1 Line 5 : User record position (1-based)
  131. // James Coyle Line 6 : User's real name
  132. // g00r00 Line 7 : User's handle/alias
  133. // 255 Line 8 : User's security level
  134. // 58 Line 9 : User's time left (in minutes)
  135. // 1 Line 11: Current node number
  136. d.Config.Comm_type, err = strconv.Atoi(lines[0])
  137. if err != nil {
  138. log.Panicf("Door32 Comm Type (expected integer): %s\n", err)
  139. }
  140. d.Config.Comm_handle, err = strconv.Atoi(lines[1])
  141. if err != nil {
  142. log.Panicf("Door32 Comm Handle (expected integer): %s\n", err)
  143. }
  144. d.Config.BBSID = lines[3]
  145. d.Config.User_number, err = strconv.Atoi(lines[4])
  146. if err != nil {
  147. log.Panicf("Door32 User Number (expected integer): %s\n", err)
  148. }
  149. d.Config.Real_name = lines[5]
  150. d.Config.Handle = lines[6]
  151. d.Config.Security_level, err = strconv.Atoi(lines[7])
  152. if err != nil {
  153. log.Panicf("Door32 Security Level (expected integer): %s\n", err)
  154. }
  155. d.Config.Time_left, err = strconv.Atoi(lines[8])
  156. if err != nil {
  157. log.Panicf("Door32 Time Left (expected integer): %s\n", err)
  158. }
  159. d.Config.Node, err = strconv.Atoi(lines[10])
  160. if err != nil {
  161. log.Panicf("Door32 Node Number (expected integer): %s\n", err)
  162. }
  163. } else if isDoorSys {
  164. // Door.sys:
  165. // Line 1: COM1: Comm Port, COM0: = LOCAL MODE
  166. // Line 4: 1 Node Number
  167. // Line 10: Rick Greer User Full Name
  168. // Line 11: Lewisville, Tx. Calling From
  169. // Line 15: 110 Security Level
  170. // Line 18: 7560 Seconds Remaining
  171. // Line 19: 126 Minutes Remaining
  172. // Line 26: 1 User File's Record Number
  173. // Line 35: Michael Sysop's Name
  174. // Line 36: Stud Alias name
  175. if lines[0] == "COM0:" {
  176. d.Config.Comm_type = 0
  177. }
  178. d.Config.Node, err = strconv.Atoi(lines[3])
  179. if err != nil {
  180. log.Panicf("Door.sys Node Number (expected integer): %s\n", err)
  181. }
  182. d.Config.Real_name = lines[9]
  183. d.Config.User_number, err = strconv.Atoi(lines[25])
  184. if err != nil {
  185. log.Panicf("Door.sys User Number (expected integer): %s\n", err)
  186. }
  187. d.Config.Handle = lines[35]
  188. d.Config.Security_level, err = strconv.Atoi(lines[14])
  189. if err != nil {
  190. log.Panicf("Door.sys Security Level (expected integer): %s\n", err)
  191. }
  192. d.Config.Time_left, err = strconv.Atoi(lines[18])
  193. if err != nil {
  194. log.Panicf("Door.sys Time Left (expected integer): %s\n", err)
  195. }
  196. }
  197. if d.Config.Comm_type == 0 {
  198. d.READFD = 0
  199. d.WRITEFD = 1
  200. } else if d.Config.Comm_type == 2 {
  201. d.READFD = d.Config.Comm_handle
  202. d.WRITEFD = d.Config.Comm_handle
  203. } else {
  204. log.Panicf("Unsupported Comm type %d\n", d.Config.Comm_type)
  205. }
  206. d.StartTime = time.Now()
  207. // Calculate when time expires.
  208. d.TimeOut = time.Now().Add(time.Duration(d.Config.Time_left) * time.Minute)
  209. }