piclaw 0.0.19 → 0.0.21

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (270) hide show
  1. package/.output/nitro.json +1 -1
  2. package/.output/public/assets/defult-D5RLDUrI.js +1 -0
  3. package/.output/public/assets/{dist-CMBqBOCp.js → dist-BH_oa-kv.js} +1 -1
  4. package/.output/public/assets/index-7JvURuHy.js +204 -0
  5. package/.output/public/assets/index-K43slwjJ.css +1 -0
  6. package/.output/public/index.html +11 -2
  7. package/.output/server/_...path_.get.mjs +16 -0
  8. package/.output/server/_chunks/app.mjs +261 -181
  9. package/.output/server/_chunks/browser.mjs +4 -1
  10. package/.output/server/_chunks/config.mjs +4 -0
  11. package/.output/server/_chunks/db.mjs +32 -28
  12. package/.output/server/_chunks/device-bus.mjs +123 -0
  13. package/.output/server/_chunks/dummy.mjs +1 -1
  14. package/.output/server/_chunks/logger.mjs +23 -0
  15. package/.output/server/_chunks/login.mjs +1 -1
  16. package/.output/server/_chunks/notes.mjs +1 -3
  17. package/.output/server/_chunks/renderer-template.mjs +1 -1
  18. package/.output/server/_chunks/sandbox.mjs +217 -0
  19. package/.output/server/_chunks/server.mjs +2302 -122
  20. package/.output/server/_chunks/terminal.mjs +63 -8
  21. package/.output/server/_chunks/uploads.mjs +60 -0
  22. package/.output/server/_chunks/virtual.mjs +192 -54
  23. package/.output/server/_id_.delete.mjs +5 -2
  24. package/.output/server/_id_.patch.mjs +2 -0
  25. package/.output/server/_id_2.delete.mjs +8 -0
  26. package/.output/server/_jid_.delete.mjs +5 -2
  27. package/.output/server/_jid_.patch.mjs +37 -4
  28. package/.output/server/_jid_2.delete.mjs +5 -2
  29. package/.output/server/_libs/@acemir/cssom+[...].mjs +2269 -1137
  30. package/.output/server/_libs/@google/genai.mjs +337 -273
  31. package/.output/server/_libs/@mariozechner/pi-agent-core+[...].mjs +381 -2073
  32. package/.output/server/_libs/@mariozechner/pi-coding-agent+[...].mjs +231 -131
  33. package/.output/server/_libs/_.mjs +3 -2
  34. package/.output/server/_libs/_10.mjs +2 -4
  35. package/.output/server/_libs/_11.mjs +2 -4
  36. package/.output/server/_libs/_12.mjs +2 -3
  37. package/.output/server/_libs/_13.mjs +2 -3
  38. package/.output/server/_libs/_14.mjs +2 -4
  39. package/.output/server/_libs/_15.mjs +2 -4
  40. package/.output/server/_libs/_16.mjs +2 -3
  41. package/.output/server/_libs/_17.mjs +2 -4
  42. package/.output/server/_libs/_18.mjs +2 -2
  43. package/.output/server/_libs/_19.mjs +2 -2
  44. package/.output/server/_libs/_2.mjs +3 -3
  45. package/.output/server/_libs/_20.mjs +2 -2
  46. package/.output/server/_libs/_21.mjs +2 -2
  47. package/.output/server/_libs/_22.mjs +2 -2
  48. package/.output/server/_libs/_23.mjs +2 -2
  49. package/.output/server/_libs/_24.mjs +2 -2
  50. package/.output/server/_libs/_25.mjs +2 -2
  51. package/.output/server/_libs/_26.mjs +2 -2
  52. package/.output/server/_libs/_27.mjs +2 -2
  53. package/.output/server/_libs/_28.mjs +2 -2
  54. package/.output/server/_libs/_29.mjs +2 -2
  55. package/.output/server/_libs/_3.mjs +3 -3
  56. package/.output/server/_libs/_30.mjs +2 -2
  57. package/.output/server/_libs/_31.mjs +2 -2
  58. package/.output/server/_libs/_32.mjs +2 -2
  59. package/.output/server/_libs/_33.mjs +2 -2
  60. package/.output/server/_libs/_34.mjs +2 -2
  61. package/.output/server/_libs/_35.mjs +2 -2
  62. package/.output/server/_libs/_36.mjs +2 -2
  63. package/.output/server/_libs/_37.mjs +2 -2
  64. package/.output/server/_libs/_38.mjs +2 -2
  65. package/.output/server/_libs/_39.mjs +2 -2
  66. package/.output/server/_libs/_4.mjs +4 -3
  67. package/.output/server/_libs/_40.mjs +2 -2
  68. package/.output/server/_libs/_41.mjs +2 -2
  69. package/.output/server/_libs/_42.mjs +2 -2
  70. package/.output/server/_libs/_43.mjs +2 -2
  71. package/.output/server/_libs/_44.mjs +2 -2
  72. package/.output/server/_libs/_45.mjs +2 -2
  73. package/.output/server/_libs/_46.mjs +2 -2
  74. package/.output/server/_libs/_47.mjs +2 -2
  75. package/.output/server/_libs/_48.mjs +2 -2
  76. package/.output/server/_libs/_49.mjs +2 -2
  77. package/.output/server/_libs/_5.mjs +2 -3
  78. package/.output/server/_libs/_50.mjs +2 -2
  79. package/.output/server/_libs/_51.mjs +2 -2
  80. package/.output/server/_libs/_52.mjs +2 -2
  81. package/.output/server/_libs/_53.mjs +2 -2
  82. package/.output/server/_libs/_54.mjs +2 -2
  83. package/.output/server/_libs/_55.mjs +2 -2
  84. package/.output/server/_libs/_56.mjs +2 -2
  85. package/.output/server/_libs/_57.mjs +2 -2
  86. package/.output/server/_libs/_58.mjs +2 -2
  87. package/.output/server/_libs/_59.mjs +2 -2
  88. package/.output/server/_libs/_6.mjs +2 -3
  89. package/.output/server/_libs/_60.mjs +2 -2
  90. package/.output/server/_libs/_61.mjs +2 -2
  91. package/.output/server/_libs/_62.mjs +2 -2
  92. package/.output/server/_libs/_63.mjs +2 -2
  93. package/.output/server/_libs/_64.mjs +2 -2
  94. package/.output/server/_libs/_65.mjs +2 -2
  95. package/.output/server/_libs/_66.mjs +2 -2
  96. package/.output/server/_libs/_67.mjs +2 -2
  97. package/.output/server/_libs/_68.mjs +2 -2
  98. package/.output/server/_libs/_69.mjs +2 -2
  99. package/.output/server/_libs/_7.mjs +2 -5
  100. package/.output/server/_libs/_70.mjs +2 -2
  101. package/.output/server/_libs/_71.mjs +2 -2
  102. package/.output/server/_libs/_72.mjs +2 -2
  103. package/.output/server/_libs/_73.mjs +2 -2
  104. package/.output/server/_libs/_74.mjs +2 -2
  105. package/.output/server/_libs/_75.mjs +2 -2
  106. package/.output/server/_libs/_76.mjs +2 -2
  107. package/.output/server/_libs/_77.mjs +2 -2
  108. package/.output/server/_libs/_78.mjs +2 -2
  109. package/.output/server/_libs/_79.mjs +2 -2
  110. package/.output/server/_libs/_8.mjs +2 -3
  111. package/.output/server/_libs/_80.mjs +2 -2
  112. package/.output/server/_libs/_81.mjs +2 -2
  113. package/.output/server/_libs/_82.mjs +2 -2
  114. package/.output/server/_libs/_83.mjs +2 -2
  115. package/.output/server/_libs/_84.mjs +2 -2
  116. package/.output/server/_libs/_85.mjs +2 -2
  117. package/.output/server/_libs/_86.mjs +2 -2
  118. package/.output/server/_libs/_87.mjs +2 -2
  119. package/.output/server/_libs/_88.mjs +2 -2
  120. package/.output/server/_libs/_89.mjs +2 -2
  121. package/.output/server/_libs/_9.mjs +2 -4
  122. package/.output/server/_libs/_90.mjs +5 -2
  123. package/.output/server/_libs/_91.mjs +3 -2
  124. package/.output/server/_libs/_92.mjs +2 -2
  125. package/.output/server/_libs/_93.mjs +2 -2
  126. package/.output/server/_libs/_94.mjs +2 -2
  127. package/.output/server/_libs/agent-base.mjs +1 -1
  128. package/.output/server/_libs/cheerio+[...].mjs +1 -1
  129. package/.output/server/_libs/data-uri-to-buffer.mjs +2 -67
  130. package/.output/server/_libs/data-urls+[...].mjs +1 -1
  131. package/.output/server/_libs/diff.mjs +1 -1
  132. package/.output/server/_libs/exodus__bytes.mjs +99 -81
  133. package/.output/server/_libs/fetch-blob+node-domexception.mjs +1 -1
  134. package/.output/server/_libs/h3+rou3+srvx.mjs +34 -4
  135. package/.output/server/_libs/html-encoding-sniffer.mjs +1 -1
  136. package/.output/server/_libs/https-proxy-agent.mjs +2 -2
  137. package/.output/server/_libs/jsdom.mjs +1 -1
  138. package/.output/server/_libs/just-bash+[...].mjs +4676 -3916
  139. package/.output/server/_libs/mariozechner__jiti.mjs +1 -1
  140. package/.output/server/_libs/mariozechner__pi-ai.mjs +1472 -0
  141. package/.output/server/_libs/md4x.mjs +1 -1
  142. package/.output/server/_libs/mime.mjs +838 -1
  143. package/.output/server/_libs/node-fetch.mjs +4 -4
  144. package/.output/server/_libs/node-liblzma.mjs +1 -1
  145. package/.output/server/_libs/silvia-odwyer__photon-node.mjs +1 -1
  146. package/.output/server/_routes/api/auth/approve.mjs +2 -0
  147. package/.output/server/_routes/api/auth/revoke.mjs +2 -0
  148. package/.output/server/_routes/api/auth/status.mjs +25 -6
  149. package/.output/server/_routes/api/browser2.mjs +1 -1
  150. package/.output/server/_routes/api/config2.mjs +2 -0
  151. package/.output/server/_routes/api/device_events.mjs +36 -0
  152. package/.output/server/_routes/api/files/groups.mjs +1 -2
  153. package/.output/server/_routes/api/files/raw.mjs +1 -1
  154. package/.output/server/_routes/api/groups.mjs +5 -3
  155. package/.output/server/_routes/api/groups2.mjs +18 -6
  156. package/.output/server/_routes/api/health.mjs +1 -2
  157. package/.output/server/_routes/api/messages.mjs +7 -1
  158. package/.output/server/_routes/api/notes/delete.mjs +4 -1
  159. package/.output/server/_routes/api/notes/write.mjs +2 -0
  160. package/.output/server/_routes/api/ntfy/setup.mjs +8 -0
  161. package/.output/server/_routes/api/pi/apikey.mjs +3 -2
  162. package/.output/server/_routes/api/pi/apikey_providers.mjs +1 -2
  163. package/.output/server/_routes/api/pi/commands.mjs +13 -3
  164. package/.output/server/_routes/api/pi/login/events.mjs +0 -1
  165. package/.output/server/_routes/api/pi/login/respond.mjs +2 -1
  166. package/.output/server/_routes/api/pi/login.mjs +1 -2
  167. package/.output/server/_routes/api/pi/logout.mjs +2 -1
  168. package/.output/server/_routes/api/pi/models.mjs +1 -2
  169. package/.output/server/_routes/api/pi/models_config2.mjs +2 -0
  170. package/.output/server/_routes/api/pi/settings2.mjs +2 -0
  171. package/.output/server/_routes/api/pi/status.mjs +1 -2
  172. package/.output/server/_routes/api/proxy.mjs +19 -1
  173. package/.output/server/_routes/api/sandbox.mjs +26 -0
  174. package/.output/server/_routes/api/sandbox2.mjs +17 -0
  175. package/.output/server/_routes/api/send.mjs +26 -18
  176. package/.output/server/_routes/api/status.mjs +1 -3
  177. package/.output/server/_routes/api/stop.mjs +11 -0
  178. package/.output/server/_routes/api/store/plugins.mjs +75 -0
  179. package/.output/server/_routes/api/store/skills.mjs +11 -0
  180. package/.output/server/_routes/api/tasks2.mjs +3 -2
  181. package/.output/server/_routes/api/telegram/setup.mjs +5 -2
  182. package/.output/server/_routes/api/telegram/status.mjs +1 -2
  183. package/.output/server/_routes/api/terminal2.mjs +2 -1
  184. package/.output/server/_routes/api/tunnel/setup.mjs +4 -2
  185. package/.output/server/_runtime.mjs +1 -2
  186. package/.output/server/_utils.mjs +10 -2
  187. package/.output/server/index.mjs +1 -1
  188. package/.output/server/node_modules/amdefine/amdefine.js +301 -0
  189. package/.output/server/node_modules/amdefine/package.json +16 -0
  190. package/.output/server/node_modules/compressjs/lib/BWT.js +420 -0
  191. package/.output/server/node_modules/compressjs/lib/BWTC.js +234 -0
  192. package/.output/server/node_modules/compressjs/lib/BitStream.js +108 -0
  193. package/.output/server/node_modules/compressjs/lib/Bzip2.js +936 -0
  194. package/.output/server/node_modules/compressjs/lib/CRC32.js +105 -0
  195. package/.output/server/node_modules/compressjs/lib/Context1Model.js +56 -0
  196. package/.output/server/node_modules/compressjs/lib/DefSumModel.js +152 -0
  197. package/.output/server/node_modules/compressjs/lib/DeflateDistanceModel.js +55 -0
  198. package/.output/server/node_modules/compressjs/lib/Dmc.js +197 -0
  199. package/.output/server/node_modules/compressjs/lib/DummyRangeCoder.js +81 -0
  200. package/.output/server/node_modules/compressjs/lib/FenwickModel.js +194 -0
  201. package/.output/server/node_modules/compressjs/lib/Huffman.js +514 -0
  202. package/.output/server/node_modules/compressjs/lib/HuffmanAllocator.js +227 -0
  203. package/.output/server/node_modules/compressjs/lib/LogDistanceModel.js +46 -0
  204. package/.output/server/node_modules/compressjs/lib/Lzjb.js +300 -0
  205. package/.output/server/node_modules/compressjs/lib/LzjbR.js +241 -0
  206. package/.output/server/node_modules/compressjs/lib/Lzp3.js +273 -0
  207. package/.output/server/node_modules/compressjs/lib/MTFModel.js +208 -0
  208. package/.output/server/node_modules/compressjs/lib/NoModel.js +46 -0
  209. package/.output/server/node_modules/compressjs/lib/PPM.js +343 -0
  210. package/.output/server/node_modules/compressjs/lib/RangeCoder.js +238 -0
  211. package/.output/server/node_modules/compressjs/lib/Simple.js +111 -0
  212. package/.output/server/node_modules/compressjs/lib/Stream.js +53 -0
  213. package/.output/server/node_modules/compressjs/lib/Util.js +324 -0
  214. package/.output/server/node_modules/compressjs/lib/freeze.js +14 -0
  215. package/.output/server/node_modules/compressjs/main.js +29 -0
  216. package/.output/server/node_modules/compressjs/package.json +35 -0
  217. package/.output/server/package.json +2 -1
  218. package/README.md +10 -1
  219. package/lib/index.d.mts +1 -0
  220. package/lib/index.mjs +1 -0
  221. package/lib/piclaw.mjs +100 -0
  222. package/lib/utils.mjs +96 -0
  223. package/package.json +16 -11
  224. package/.output/public/assets/defult-CMO6TZ5a.js +0 -1
  225. package/.output/public/assets/index-jdnbJw-M.js +0 -204
  226. package/.output/public/assets/index-ooXrRwgl.css +0 -1
  227. package/.output/server/_chunks/commands.mjs +0 -282
  228. package/.output/server/_chunks/pi.mjs +0 -202
  229. package/.output/server/_chunks/session.mjs +0 -1114
  230. package/.output/server/_libs/@aws-crypto/crc32+[...].mjs +0 -299
  231. package/.output/server/_libs/@aws-sdk/client-bedrock-runtime+[...].mjs +0 -17828
  232. package/.output/server/_libs/@aws-sdk/credential-provider-http+[...].mjs +0 -122
  233. package/.output/server/_libs/@aws-sdk/credential-provider-ini+[...].mjs +0 -417
  234. package/.output/server/_libs/@aws-sdk/credential-provider-process+[...].mjs +0 -54
  235. package/.output/server/_libs/@aws-sdk/credential-provider-sso+[...].mjs +0 -1151
  236. package/.output/server/_libs/@aws-sdk/credential-provider-web-identity+[...].mjs +0 -50
  237. package/.output/server/_libs/@smithy/credential-provider-imds+[...].mjs +0 -369
  238. package/.output/server/_libs/@tootallnate/quickjs-emscripten+[...].mjs +0 -3011
  239. package/.output/server/_libs/_100.mjs +0 -2
  240. package/.output/server/_libs/_101.mjs +0 -2
  241. package/.output/server/_libs/_102.mjs +0 -5
  242. package/.output/server/_libs/_103.mjs +0 -3
  243. package/.output/server/_libs/_104.mjs +0 -2
  244. package/.output/server/_libs/_105.mjs +0 -3
  245. package/.output/server/_libs/_106.mjs +0 -2
  246. package/.output/server/_libs/_107.mjs +0 -2
  247. package/.output/server/_libs/_95.mjs +0 -2
  248. package/.output/server/_libs/_96.mjs +0 -2
  249. package/.output/server/_libs/_97.mjs +0 -2
  250. package/.output/server/_libs/_98.mjs +0 -2
  251. package/.output/server/_libs/_99.mjs +0 -2
  252. package/.output/server/_libs/amdefine.mjs +0 -188
  253. package/.output/server/_libs/ast-types.mjs +0 -2270
  254. package/.output/server/_libs/aws-sdk__nested-clients.mjs +0 -3141
  255. package/.output/server/_libs/basic-ftp.mjs +0 -1906
  256. package/.output/server/_libs/compressjs.mjs +0 -50
  257. package/.output/server/_libs/degenerator+[...].mjs +0 -9964
  258. package/.output/server/_libs/get-uri.mjs +0 -413
  259. package/.output/server/_libs/http-proxy-agent.mjs +0 -123
  260. package/.output/server/_libs/ip-address.mjs +0 -1423
  261. package/.output/server/_libs/lru-cache.mjs +0 -732
  262. package/.output/server/_libs/netmask.mjs +0 -139
  263. package/.output/server/_libs/pac-proxy-agent+[...].mjs +0 -3104
  264. package/.output/server/_libs/proxy-agent+proxy-from-env.mjs +0 -204
  265. package/.output/server/_libs/smithy__core.mjs +0 -192
  266. package/.output/server/node_modules/tslib/modules/index.js +0 -70
  267. package/.output/server/node_modules/tslib/modules/package.json +0 -3
  268. package/.output/server/node_modules/tslib/package.json +0 -47
  269. package/.output/server/node_modules/tslib/tslib.js +0 -484
  270. package/bin/piclaw.mjs +0 -195
@@ -0,0 +1,194 @@
1
+ /** Range coding model based on Fenwick trees for O(ln N) query/update. */
2
+ if (typeof define !== 'function') { var define = require('amdefine')(module); }
3
+ define(['./RangeCoder','./Stream','./Util'],function(RangeCoder,Stream,Util){
4
+
5
+ /** We store two probabilities in a U32, so max prob is going to be 0xFFFF */
6
+ var DEFAULT_MAX_PROB = 0xFF00;
7
+ var DEFAULT_INCREMENT= 0x0100;
8
+
9
+ var ESC_MASK = 0x0000FFFF, ESC_SHIFT = 0;
10
+ var SYM_MASK = 0xFFFF0000, SYM_SHIFT = 16;
11
+ var SCALE_MASK=0xFFFEFFFE;
12
+
13
+ var FenwickModel = function(coder, size, max_prob, increment) {
14
+ this.coder = coder;
15
+ this.numSyms = size + 1; // save space for an escape symbol
16
+ this.tree = Util.makeU32Buffer(this.numSyms*2);
17
+ this.increment = (+increment) || DEFAULT_INCREMENT;
18
+ this.max_prob = (+max_prob) || DEFAULT_MAX_PROB;
19
+ // sanity-check to prevent overflow.
20
+ console.assert((this.max_prob + (this.increment-1)) <= 0xFFFF);
21
+ console.assert(size <= 0xFFFF);
22
+ // record escape probability as 1.
23
+ var i;
24
+ for (i=0; i<size; i++) {
25
+ this.tree[this.numSyms + i] = // escape prob=1, sym prob = 0
26
+ (1 << ESC_SHIFT) | (0 << SYM_SHIFT);
27
+ }
28
+ this.tree[this.numSyms + i] = // escape prob = 0, sym prob = 1
29
+ (0 << ESC_SHIFT) | (this.increment << SYM_SHIFT);
30
+ this._sumTree();
31
+ // probability sums are in this.tree[1]. this.tree[0] is unused.
32
+ };
33
+ FenwickModel.factory = function(coder, max_prob, increment) {
34
+ return function(size) {
35
+ return new FenwickModel(coder, size, max_prob, increment);
36
+ };
37
+ };
38
+ FenwickModel.prototype.clone = function() {
39
+ var newModel = new FenwickModel(this.coder, this.size,
40
+ this.max_prob, this.increment);
41
+ var i;
42
+ for (i=1; i<this.tree.length; i++) {
43
+ newModel.tree[i] = this.tree[i];
44
+ }
45
+ return newModel;
46
+ };
47
+ FenwickModel.prototype.encode = function(symbol) {
48
+ var i = this.numSyms + symbol;
49
+ var sy_f = this.tree[i];
50
+ var mask = SYM_MASK, shift = SYM_SHIFT;
51
+ var update = (this.increment << SYM_SHIFT);
52
+
53
+ if ((sy_f & SYM_MASK) === 0) { // escape!
54
+ this.encode(this.numSyms-1);
55
+ mask = ESC_MASK;
56
+ update -= (1<<ESC_SHIFT); // not going to escape no mo'
57
+ shift = ESC_SHIFT;
58
+ } else if (symbol === (this.numSyms-1) &&
59
+ ((this.tree[1] & ESC_MASK) >>> ESC_SHIFT) === 1) {
60
+ // this is the last escape, zero it out
61
+ update = -this.tree[i];
62
+ }
63
+ // sum up the proper lt_f
64
+ var lt_f = 0;
65
+ while (i > 1) {
66
+ var isRight = (i & 1);
67
+ var parent = (i >>> 1);
68
+ // if we're the right child, we need to
69
+ // add the prob from the left child
70
+ if (isRight) {
71
+ lt_f += this.tree[2*parent];
72
+ }
73
+ // update sums
74
+ this.tree[i] += update; // increase sym / decrease esc
75
+ i = parent;
76
+ }
77
+ var tot_f = this.tree[1];
78
+ this.tree[1] += update; // update prob in root
79
+ sy_f = (sy_f & mask) >>> shift;
80
+ lt_f = (lt_f & mask) >>> shift;
81
+ tot_f =(tot_f& mask) >>> shift;
82
+ this.coder.encodeFreq(sy_f, lt_f, tot_f);
83
+ // rescale?
84
+ if ((( this.tree[1] & SYM_MASK ) >>> SYM_SHIFT) >= this.max_prob) {
85
+ this._rescale();
86
+ }
87
+ };
88
+ FenwickModel.prototype._decode = function(isEscape) {
89
+ var mask = SYM_MASK, shift = SYM_SHIFT;
90
+ var update = (this.increment << SYM_SHIFT);
91
+ if (isEscape) {
92
+ mask = ESC_MASK;
93
+ update -= (1 << ESC_SHIFT);
94
+ shift = ESC_SHIFT;
95
+ }
96
+ var tot_f = (this.tree[1] & mask) >>> shift;
97
+ var prob = this.coder.decodeCulFreq(tot_f);
98
+ // travel down the tree looking for this
99
+ var i = 1, lt_f = 0;
100
+ while (i < this.numSyms) {
101
+ this.tree[i] += update;
102
+ // look at probability in left child.
103
+ var leftProb = (this.tree[2*i] & mask) >>> shift;
104
+ i *= 2;
105
+ if ((prob-lt_f) >= leftProb) {
106
+ lt_f += leftProb;
107
+ i++; // take the right child.
108
+ }
109
+ }
110
+ var symbol = i - this.numSyms;
111
+ var sy_f = (this.tree[i] & mask) >>> shift;
112
+ this.tree[i] += update;
113
+ this.coder.decodeUpdate(sy_f, lt_f, tot_f);
114
+ // was this the last escape?
115
+ if (symbol === (this.numSyms-1) &&
116
+ ((this.tree[1] & ESC_MASK) >>> ESC_SHIFT) === 1) {
117
+ update = -this.tree[i]; // zero it out
118
+ while (i >= 1) {
119
+ this.tree[i] += update;
120
+ i = (i >>> 1); // parent
121
+ }
122
+ }
123
+ // rescale?
124
+ if ((( this.tree[1] & SYM_MASK ) >>> SYM_SHIFT) >= this.max_prob) {
125
+ this._rescale();
126
+ }
127
+ return symbol;
128
+ };
129
+ FenwickModel.prototype.decode = function() {
130
+ var symbol = this._decode(false); // not escape
131
+ if (symbol === (this.numSyms-1)) {
132
+ // this was an escape!
133
+ symbol = this._decode(true); // an escape!
134
+ }
135
+ return symbol;
136
+ };
137
+ FenwickModel.prototype._rescale = function() {
138
+ var i, prob, noEscape = true;
139
+ // scale symbols (possible causing them to escape)
140
+ for (i=0; i < this.numSyms-1; i++) {
141
+ prob = this.tree[this.numSyms + i];
142
+ if ((prob & ESC_MASK) !== 0) {
143
+ // this symbol escapes
144
+ noEscape = false;
145
+ continue;
146
+ }
147
+ prob = (prob & SCALE_MASK) >>> 1;
148
+ if (prob === 0) {
149
+ // this symbol newly escapes
150
+ prob = (1 << ESC_SHIFT);
151
+ noEscape = false;
152
+ }
153
+ this.tree[this.numSyms + i] = prob;
154
+ }
155
+ // scale the escape symbol
156
+ prob = this.tree[this.numSyms + i];
157
+ prob = (prob & SCALE_MASK) >>> 1;
158
+ // prob should be zero if there are no escaping symbols, otherwise
159
+ // it must be at least 1.
160
+ if (noEscape) { prob = 0; }
161
+ else if (prob === 0) { prob = (1 << SYM_SHIFT); }
162
+ this.tree[this.numSyms + i] = prob;
163
+ // sum it all up afresh
164
+ this._sumTree();
165
+ };
166
+ FenwickModel.prototype._sumTree = function() {
167
+ var i;
168
+ // sum it all. (we know we won't overflow)
169
+ for (i=this.numSyms - 1; i > 0; i--) {
170
+ this.tree[i] = this.tree[2*i] + this.tree[2*i + 1];
171
+ }
172
+ };
173
+
174
+ FenwickModel.MAGIC = 'fenw';
175
+ /** Simple order-0 compressor, as self-test. */
176
+ FenwickModel.compressFile = Util.compressFileHelper(FenwickModel.MAGIC, function(inStream, outStream, fileSize, props, finalByte) {
177
+ var range = new RangeCoder(outStream);
178
+ range.encodeStart(finalByte, 1);
179
+ var model = new FenwickModel(range, (fileSize<0) ? 257 : 256);
180
+ Util.compressWithModel(inStream, fileSize, model);
181
+ range.encodeFinish();
182
+ }, true);
183
+
184
+ /** Simple order-0 decompresser, as self-test. */
185
+ FenwickModel.decompressFile = Util.decompressFileHelper(FenwickModel.MAGIC, function(inStream, outStream, fileSize) {
186
+ var range = new RangeCoder(inStream);
187
+ range.decodeStart(true/*already read the final byte*/);
188
+ var model = new FenwickModel(range, (fileSize<0) ? 257 : 256);
189
+ Util.decompressWithModel(outStream, fileSize, model);
190
+ range.decodeFinish();
191
+ });
192
+
193
+ return FenwickModel;
194
+ });
@@ -0,0 +1,514 @@
1
+ /* Adaptive Huffman code, using Vitter's algorithm ported from
2
+ * vitter.c at http://code.google.com/p/compression-code/downloads/list
3
+ * The original code was placed in the public domain, and so I
4
+ * also place this JavaScript port in the public domain.
5
+ * -- C. Scott Ananian <cscott@cscott.net>, 2013
6
+ * ps. some truly grotty C code in the originally, faithfully ported to
7
+ * evil comma-operator-using, assignment-in-if-condition JavaScript.
8
+ */
9
+ if (typeof define !== 'function') { var define = require('amdefine')(module); }
10
+ define(['./BitStream','./Util'],function(BitStream,Util) {
11
+ // This code is adapted from Professor Vitter's
12
+ // article, Design and Analysis of Dynamic Huffman Codes,
13
+ // which appeared in JACM October 1987
14
+
15
+ // A design trade-off has been made to simplify the
16
+ // code: a node's block is determined dynamically,
17
+ // and the implicit tree structure is maintained,
18
+ // e.g. explicit node numbers are also implicit.
19
+
20
+ // Dynamic Huffman table weight ranking
21
+ // is maintained per Professor Vitter's
22
+ // invariant (*) for algorithm FGK:
23
+
24
+ // leaves precede internal nodes of the
25
+ // same weight in a non-decreasing ranking
26
+ // of weights using implicit node numbers:
27
+
28
+ // 1) leaves slide over internal nodes, internal nodes
29
+ // swap over groups of leaves, leaves are swapped
30
+ // into group leader position, but two internal
31
+ // nodes never change positions relative
32
+ // to one another.
33
+
34
+ // 2) weights are incremented by 2:
35
+ // leaves always have even weight values;
36
+ // internal nodes always have odd values.
37
+
38
+ // 3) even node numbers are always right children;
39
+ // odd numbers are left children in the tree.
40
+
41
+ // node 2 * HuffSize - 1 is always the tree root;
42
+ // node HuffEsc is the escape node;
43
+
44
+ // the tree is initialized by creating an
45
+ // escape node as the root.
46
+
47
+ // each new leaf symbol is paired with a new escape
48
+ // node into the previous escape node in the tree,
49
+ // until the last symbol which takes over the
50
+ // tree position of the escape node, and
51
+ // HuffEsc is left at zero.
52
+
53
+ // overall table size: 2 * HuffSize
54
+
55
+ // huff_init(alphabet_size, potential symbols used)
56
+ // huff_encode(next_symbol)
57
+ // next_symbol = huff_decode()
58
+
59
+ // huff_scale(by_bits) -- scale weights and re-balance tree
60
+
61
+ var HTable = function(up, down, symbol, weight) {
62
+ this.up = up; // next node up the tree
63
+ this.down = down; // pair of down nodes
64
+ this.symbol = symbol; // node symbol value
65
+ this.weight = weight; // node weight
66
+ };
67
+ HTable.prototype.clone = function() {
68
+ return new HTable(this.up, this.down, this.symbol, this.weight);
69
+ };
70
+ HTable.prototype.set = function(htable) {
71
+ this.up = htable.up;
72
+ this.down = htable.down;
73
+ this.symbol = htable.symbol;
74
+ this.weight = htable.weight;
75
+ };
76
+
77
+ // initialize an adaptive coder
78
+ // for alphabet size, and count
79
+ // of nodes to be used
80
+ var Huffman = function(size, root, bitstream, max_weight) {
81
+ var i;
82
+ // default: all alphabet symbols are used
83
+
84
+ console.assert(size && typeof(size)==='number');
85
+ if( !root || root > size )
86
+ root = size;
87
+
88
+ // create the initial escape node
89
+ // at the tree root
90
+
91
+ if ( root <<= 1 ) {
92
+ root--;
93
+ }
94
+
95
+ // create root+1 htables (coding table)
96
+ // XXX this could be views on a backing Uint32 array?
97
+ this.table = [];
98
+ for (i=0; i<=root; i++) {
99
+ this.table[i] = new HTable(0,0,0,0);
100
+ }
101
+
102
+ // this.map => mapping for symbols to nodes
103
+ this.map = [];
104
+ // this.size => the alphabet size
105
+ if( this.size = size ) {
106
+ for (i=0; i<size; i++) {
107
+ this.map[i] = 0;
108
+ }
109
+ }
110
+
111
+ // this.esc => the current tree height
112
+ // this.root => the root of the tree
113
+ this.esc = this.root = root;
114
+
115
+ if (bitstream) {
116
+ this.readBit = bitstream.readBit.bind(bitstream);
117
+ this.writeBit = bitstream.writeBit.bind(bitstream);
118
+ }
119
+ this.max_weight = max_weight; // may be null or undefined
120
+ }
121
+ // factory interface
122
+ Huffman.factory = function(bitstream, max_weight) {
123
+ return function(size) {
124
+ return new Huffman(size, size, bitstream, max_weight);
125
+ };
126
+ };
127
+
128
+
129
+ // split escape node to incorporate new symbol
130
+
131
+ Huffman.prototype.split = function(symbol) {
132
+ var pair, node;
133
+
134
+ // is the tree already full???
135
+
136
+ if( pair = this.esc ) {
137
+ this.esc--;
138
+ } else {
139
+ console.assert(false);
140
+ return 0;
141
+ }
142
+
143
+ // if this is the last symbol, it moves into
144
+ // the escape node's old position, and
145
+ // this.esc is set to zero.
146
+
147
+ // otherwise, the escape node is promoted to
148
+ // parent a new escape node and the new symbol.
149
+
150
+ if( node = this.esc ) {
151
+ this.table[pair].down = node;
152
+ this.table[pair].weight = 1;
153
+ this.table[node].up = pair;
154
+ this.esc--;
155
+ } else {
156
+ pair = 0;
157
+ node = 1;
158
+ }
159
+
160
+ // initialize the new symbol node
161
+
162
+ this.table[node].symbol = symbol;
163
+ this.table[node].weight = 0;
164
+ this.table[node].down = 0;
165
+ this.map[symbol] = node;
166
+
167
+ // initialize a new escape node.
168
+
169
+ this.table[this.esc].weight = 0;
170
+ this.table[this.esc].down = 0;
171
+ this.table[this.esc].up = pair;
172
+ return node;
173
+ };
174
+
175
+ // swap leaf to group leader position
176
+ // return symbol's new node
177
+
178
+ Huffman.prototype.leader = function(node) {
179
+ var weight = this.table[node].weight;
180
+ var leader = node, prev, symbol;
181
+
182
+ while( weight === this.table[leader + 1].weight ) {
183
+ leader++;
184
+ }
185
+
186
+ if( leader === node ) {
187
+ return node;
188
+ }
189
+
190
+ // swap the leaf nodes
191
+
192
+ symbol = this.table[node].symbol;
193
+ prev = this.table[leader].symbol;
194
+
195
+ this.table[leader].symbol = symbol;
196
+ this.table[node].symbol = prev;
197
+ this.map[symbol] = leader;
198
+ this.map[prev] = node;
199
+ return leader;
200
+ };
201
+
202
+ // slide internal node up over all leaves of equal weight;
203
+ // or exchange leaf with next smaller weight internal node
204
+
205
+ // return node's new position
206
+
207
+ Huffman.prototype.slide = function(node) {
208
+ var next = node;
209
+ var swap;
210
+
211
+ swap = this.table[next++].clone();
212
+
213
+ // if we're sliding an internal node, find the
214
+ // highest possible leaf to exchange with
215
+
216
+ if( swap.weight & 1 ) {
217
+ while( swap.weight > this.table[next + 1].weight ) {
218
+ next++;
219
+ }
220
+ }
221
+
222
+ // swap the two nodes
223
+
224
+ this.table[node].set(this.table[next]);
225
+ this.table[next].set(swap);
226
+
227
+ this.table[next].up = this.table[node].up;
228
+ this.table[node].up = swap.up;
229
+
230
+ // repair the symbol map and tree structure
231
+
232
+ if( swap.weight & 1 ) {
233
+ this.table[swap.down].up = next;
234
+ this.table[swap.down - 1].up = next;
235
+ this.map[this.table[node].symbol] = node;
236
+ } else {
237
+ this.table[this.table[node].down - 1].up = node;
238
+ this.table[this.table[node].down].up = node;
239
+ this.map[swap.symbol] = next;
240
+ }
241
+
242
+ return next;
243
+ };
244
+
245
+ // increment symbol weight and re balance the tree.
246
+
247
+ Huffman.prototype.increment = function(node) {
248
+ var up;
249
+
250
+ // obviate swapping a parent with its child:
251
+ // increment the leaf and proceed
252
+ // directly to its parent.
253
+
254
+ // otherwise, promote leaf to group leader position in the tree
255
+
256
+ if( this.table[node].up === node + 1 ) {
257
+ this.table[node].weight += 2;
258
+ node++;
259
+ } else {
260
+ node = this.leader (node);
261
+ }
262
+
263
+ // increase the weight of each node and slide
264
+ // over any smaller weights ahead of it
265
+ // until reaching the root
266
+
267
+ // internal nodes work upwards from
268
+ // their initial positions; while
269
+ // symbol nodes slide over first,
270
+ // then work up from their final
271
+ // positions.
272
+
273
+ while( this.table[node].weight += 2, up = this.table[node].up ) {
274
+ while( this.table[node].weight > this.table[node + 1].weight ) {
275
+ node = this.slide (node);
276
+ }
277
+
278
+ if( this.table[node].weight & 1 ) {
279
+ node = up;
280
+ } else {
281
+ node = this.table[node].up;
282
+ }
283
+ }
284
+
285
+ /* Re-scale if necessary. */
286
+ if (this.max_weight) {
287
+ if (this.table[this.root].weight >= this.max_weight) {
288
+ this.scale(1);
289
+ }
290
+ }
291
+ };
292
+
293
+ // scale all weights and re-balance the tree
294
+
295
+ // zero weight nodes are removed from the tree
296
+ // by sliding them out the left of the rank list
297
+
298
+ Huffman.prototype.scale = function(bits) {
299
+ var node = this.esc, weight, prev;
300
+
301
+ // work up the tree from the escape node
302
+ // scaling weights by the value of bits
303
+
304
+ while( ++node <= this.root ) {
305
+ // recompute the weight of internal nodes;
306
+ // slide down and out any unused ones
307
+
308
+ if( this.table[node].weight & 1 ) {
309
+ if( weight = this.table[this.table[node].down].weight & ~1 ) {
310
+ weight += this.table[this.table[node].down - 1].weight | 1;
311
+ }
312
+
313
+ // remove zero weight leaves by incrementing HuffEsc
314
+ // and removing them from the symbol map. take care
315
+
316
+ } else if( !(weight = this.table[node].weight >> bits & ~1) ) {
317
+ if( this.map[this.table[node].symbol] = 0, this.esc++ ) {
318
+ this.esc++;
319
+ }
320
+ }
321
+
322
+ // slide the scaled node back down over any
323
+ // previous nodes with larger weights
324
+
325
+ this.table[node].weight = weight;
326
+ prev = node;
327
+
328
+ while( weight < this.table[--prev].weight ) {
329
+ this.slide(prev);
330
+ }
331
+ }
332
+
333
+ // prepare a new escape node
334
+
335
+ this.table[this.esc].down = 0;
336
+ };
337
+
338
+ // send the bits for an escaped symbol
339
+
340
+ Huffman.prototype.sendid = function(symbol) {
341
+ var empty = 0, max;
342
+
343
+ // count the number of empty symbols
344
+ // before the symbol in the table
345
+
346
+ while( symbol-- ) {
347
+ if( !this.map[symbol] ) {
348
+ empty++;
349
+ }
350
+ }
351
+
352
+ // send LSB of this count first, using
353
+ // as many bits as are required for
354
+ // the maximum possible count
355
+
356
+ if( max = this.size - Math.floor((this.root - this.esc) / 2) - 1 ) {
357
+ do {
358
+ this.writeBit(empty & 1);
359
+ empty >>= 1;
360
+ } while( max >>= 1 );
361
+ }
362
+ };
363
+
364
+ // encode the next symbol
365
+
366
+ Huffman.prototype.encode = function(symbol) {
367
+ var emit = 1, bit;
368
+ var up, idx, node;
369
+
370
+ if( symbol < this.size ) {
371
+ node = this.map[symbol];
372
+ } else {
373
+ console.assert(false);
374
+ return;
375
+ }
376
+
377
+ // for a new symbol, direct the receiver to the escape node
378
+ // but refuse input if table is already full.
379
+
380
+ if( !(idx = node) ) {
381
+ if( !(idx = this.esc) ) {
382
+ return;
383
+ }
384
+ }
385
+
386
+ // accumulate the code bits by
387
+ // working up the tree from
388
+ // the node to the root
389
+
390
+ while( up = this.table[idx].up ) {
391
+ emit <<= 1; emit |= idx & 1; idx = up;
392
+ }
393
+
394
+ // send the code, root selector bit first
395
+
396
+ while( bit = emit & 1, emit >>= 1 ) {
397
+ this.writeBit(bit);
398
+ }
399
+
400
+ // send identification and incorporate
401
+ // new symbols into the tree
402
+
403
+ if( !node ) {
404
+ this.sendid(symbol);
405
+ node = this.split(symbol);
406
+ }
407
+
408
+ // adjust and re-balance the tree
409
+
410
+ this.increment(node);
411
+ };
412
+
413
+ // read the identification bits
414
+ // for an escaped symbol
415
+
416
+ Huffman.prototype.readid = function() {
417
+ var empty = 0, bit = 1, max, symbol;
418
+
419
+ // receive the symbol, LSB first, reading
420
+ // only the number of bits necessary to
421
+ // transmit the maximum possible symbol value
422
+
423
+ if( max = this.size - Math.floor((this.root - this.esc) / 2) - 1 ) {
424
+ do {
425
+ empty |= this.readBit() ? bit : 0;
426
+ bit <<= 1;
427
+ } while( max >>= 1 );
428
+ }
429
+
430
+ // the count is of unmapped symbols
431
+ // in the table before the new one
432
+
433
+ for( symbol = 0; symbol < this.size; symbol++ ) {
434
+ if( !this.map[symbol] ) {
435
+ if( !empty-- ) {
436
+ return symbol;
437
+ }
438
+ }
439
+ }
440
+
441
+ // oops! our count is too big, either due
442
+ // to a bit error, or a short node count
443
+ // given to huff_init.
444
+
445
+ console.assert(false);
446
+ return 0;
447
+ };
448
+
449
+ // decode the next symbol
450
+
451
+ Huffman.prototype.decode = function() {
452
+ var node = this.root;
453
+ var symbol, down;
454
+
455
+ // work down the tree from the root
456
+ // until reaching either a leaf
457
+ // or the escape node. A one
458
+ // bit means go left, a zero
459
+ // means go right.
460
+
461
+ while( down = this.table[node].down ) {
462
+ if( this.readBit() ) {
463
+ node = down - 1; // the left child precedes the right child
464
+ } else {
465
+ node = down;
466
+ }
467
+ }
468
+
469
+ // sent to the escape node???
470
+ // refuse to add to a full tree
471
+
472
+ if( node === this.esc ) {
473
+ if( this.esc ) {
474
+ symbol = this.readid ();
475
+ node = this.split (symbol);
476
+ } else {
477
+ console.assert(false);
478
+ return 0;
479
+ }
480
+ } else {
481
+ symbol = this.table[node].symbol;
482
+ }
483
+
484
+ // increment weights and re-balance
485
+ // the coding tree
486
+
487
+ this.increment (node);
488
+ return symbol;
489
+ };
490
+
491
+ // stand alone compressor, mostly for testing
492
+ Huffman.MAGIC = 'huff';
493
+ Huffman.compressFile = Util.compressFileHelper(Huffman.MAGIC, function(input, output, size, props) {
494
+ var bitstream = new BitStream(output);
495
+
496
+ var alphabetSize = 256;
497
+ if (size < 0) { alphabetSize++; }
498
+ var huff = new Huffman(257, alphabetSize, bitstream, 8191);
499
+ Util.compressWithModel(input, size, huff);
500
+ bitstream.flush();
501
+ });
502
+
503
+ // stand alone decompresser, again for testing
504
+ Huffman.decompressFile = Util.decompressFileHelper(Huffman.MAGIC, function(input, output, size) {
505
+ var bitstream = new BitStream(input);
506
+
507
+ var alphabetSize = 256;
508
+ if (size < 0) { alphabetSize++; }
509
+ var huff = new Huffman(257, alphabetSize, bitstream, 8191);
510
+ Util.decompressWithModel(output, size, huff);
511
+ });
512
+
513
+ return Huffman;
514
+ });