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
#!/bin/env tclsh
#***
# [manpage_begin main_thread tclircc 0.0.1]
# [titledesc {Thread main}]
# [description]
# [para]
# This is the application entrypoint. It does the following.
# [list_begin itemized]
set path [file dirname [dict get [info frame 0] file]]
set version v0.0.1
proc src {file} {
global path
uplevel [list source [file join $path $file]]
}
package require Thread
thread::id; # avoid use-after-free
package require logger
set log [logger::init tclircc::main]
package require sqlite3
${log}::info "tclircc $version <https://amehut.dev/~aleteoryx/tclircc>"
${log}::info "running from $path"
#***
# [item]
# brings up the routing system
src router.tcl
proc on_routes_update {} {
puts "routes updated!"
r::debug
}
proc start_thread {name} {
global path
global version
global log
${log}::debug "starting $name thread..."
set thread [thread::create -preserved]
router::manage $thread tclircc::$name
thread::send $thread [list variable path $path version $version]
if {[thread::send $thread \
[list source [file join $path $name main.tcl] ] result] == 1} {
${log}::critical "couldn't start $name thread: $result"
exit -1
}
${log}::debug "started $name thread."
}
#***
# [item]
# brings up the database
start_thread db
thread::send [r::ns tclircc::db] {path_to_core} core_db_path
sqlite3 core_db $core_db_path -create true -fullmutex true
src migrate_core.tcl
src plugins.tcl
#***
# [item]
# loads the other core threads
start_thread irc
start_thread ui
plugins::load [file join $path .. testplugin]
#***
# [item]
# opens a window
${log}::debug "opening initial window..."
r::exec tclircc::ui {
mk_toplevel name
expr {$name}
} {
${log}::debug "initial window opened: $result"
}
${log}::info "entering event loop"
vwait nil
#***
# [list_end]
# [manpage_end]