deadbyte-mcp 0.14.0 → 0.15.1

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 (157) hide show
  1. package/AGENTS.md +11 -18
  2. package/CONTEXT.md +3 -3
  3. package/MANIFEST.SHA256 +156 -70
  4. package/PROVENANCE.json +10 -0
  5. package/R43-PARENT.json +20 -0
  6. package/R44-DONORS.json +99 -0
  7. package/R44-PARENT.json +18 -0
  8. package/R45-PARENT.json +18 -0
  9. package/README.txt +19 -14
  10. package/RELEASE.json +37 -0
  11. package/SBOM.cdx.json +46 -0
  12. package/TEST-MATRIX.json +31 -0
  13. package/bin/deadbyte-hardware-observer-r45.exe +0 -0
  14. package/bin/deadbyte-hardware-observer-r45.obj +0 -0
  15. package/controller/README.TXT +5 -6
  16. package/controller/deadbyte-controller.ps1 +2 -2
  17. package/docs/ARCHITECTURE.md +8 -1
  18. package/docs/R44-ARCHITECTURE.md +37 -0
  19. package/native/deadbyte-hardware-observer.cpp +308 -0
  20. package/package.json +18 -8
  21. package/scripts/autonomous-tests.ps1 +2 -2
  22. package/scripts/build-hardware-r45.ps1 +71 -0
  23. package/scripts/deferred-slot-operation-r43.mjs +126 -0
  24. package/scripts/deferred-slot-operation-r44.mjs +126 -0
  25. package/scripts/deferred-slot-operation-r45.mjs +126 -0
  26. package/scripts/derive-r45-parent.mjs +24 -0
  27. package/scripts/derive-r45-release.mjs +72 -0
  28. package/scripts/derive-r45-tests.mjs +20 -0
  29. package/scripts/final-closure-r43.mjs +115 -0
  30. package/scripts/final-closure-r44.mjs +121 -0
  31. package/scripts/final-closure-r45.mjs +121 -0
  32. package/scripts/final-closure-verify-r43.mjs +213 -0
  33. package/scripts/final-closure-verify-r44.mjs +220 -0
  34. package/scripts/final-closure-verify-r45.mjs +220 -0
  35. package/scripts/finalize-r43.mjs +217 -0
  36. package/scripts/finalize-r44.mjs +217 -0
  37. package/scripts/finalize-r45.mjs +219 -0
  38. package/scripts/full-regression-r43.mjs +20 -0
  39. package/scripts/full-regression-r44.mjs +20 -0
  40. package/scripts/full-regression-r45.mjs +20 -0
  41. package/scripts/full-regression-summary-r45.mjs +14 -0
  42. package/scripts/gate-windows-r43.ps1 +36 -0
  43. package/scripts/gate-windows-r44.ps1 +36 -0
  44. package/scripts/gate-windows-r45.ps1 +44 -0
  45. package/scripts/init-host-policy.ps1 +39 -1
  46. package/scripts/inspect-active-release-r45.mjs +20 -0
  47. package/scripts/release-manifest.mjs +3 -1
  48. package/scripts/release-parity-r43.mjs +218 -0
  49. package/scripts/release-parity-r44.mjs +242 -0
  50. package/scripts/release-parity-r45.mjs +253 -0
  51. package/scripts/release-parity-tests-r43.ps1 +8 -0
  52. package/scripts/release-parity-tests-r44.ps1 +8 -0
  53. package/scripts/release-parity-tests-r45.ps1 +8 -0
  54. package/scripts/verify-r43-parent.mjs +126 -0
  55. package/scripts/verify-r44-parent.mjs +142 -0
  56. package/scripts/verify-r45-parent.mjs +142 -0
  57. package/scripts/windows-gate-evidence-r43.mjs +55 -0
  58. package/scripts/windows-gate-evidence-r44.mjs +55 -0
  59. package/scripts/windows-gate-evidence-r45.mjs +60 -0
  60. package/src/agent-backend-r44.mjs +254 -0
  61. package/src/autonomous-output-contracts.mjs +1 -1
  62. package/src/autonomous-policy.mjs +41 -4
  63. package/src/autonomous-runtime.mjs +37 -19
  64. package/src/autonomous-supervisor-host.mjs +12 -2
  65. package/src/capability-ledger.mjs +3 -1
  66. package/src/codex-app-server-r44.mjs +154 -0
  67. package/src/coding-plane.mjs +66 -19
  68. package/src/compact-gateway-mcp-tools.mjs +4 -2
  69. package/src/deadbyte-cli.mjs +17 -9
  70. package/src/doctor-r45.mjs +65 -0
  71. package/src/durable-job-r44.mjs +145 -0
  72. package/src/external-job-provider-r44.mjs +126 -0
  73. package/src/host-plane.mjs +156 -87
  74. package/src/job-supervisor-host-r44.mjs +112 -0
  75. package/src/machine-fs-smoke-client.mjs +1 -1
  76. package/src/machine-fs.mjs +21 -10
  77. package/src/mcp-host-smoke-client.mjs +1 -1
  78. package/src/mcp-server.mjs +84 -26
  79. package/src/mcp-smoke-client.mjs +1 -1
  80. package/src/native-diff-v2.mjs +12 -7
  81. package/src/native-diff.mjs +32 -9
  82. package/src/observation-mcp-tools.mjs +5 -1
  83. package/src/observation-output-contracts.mjs +8 -0
  84. package/src/observation-runtime.mjs +33 -2
  85. package/src/observation-smoke-client.mjs +7 -3
  86. package/src/operator-surface.mjs +2 -2
  87. package/src/output-contracts.mjs +27 -11
  88. package/src/process-policy.mjs +19 -0
  89. package/src/process-runtime.mjs +5 -2
  90. package/src/process-smoke-client.mjs +2 -2
  91. package/src/provider-circuit.mjs +8 -2
  92. package/src/r44-compact-disarmed-probe.mjs +74 -0
  93. package/src/r44-full-surface-probe.mjs +34 -0
  94. package/src/r45-compact-disarmed-probe.mjs +74 -0
  95. package/src/r45-full-surface-probe.mjs +34 -0
  96. package/src/release-generation.mjs +1 -0
  97. package/src/remote-device-r44.mjs +205 -0
  98. package/src/remote-mcp-autonomous-smoke-client.mjs +4 -4
  99. package/src/remote-mcp-r44-parity-client.mjs +203 -0
  100. package/src/remote-mcp-r45-parity-client.mjs +206 -0
  101. package/src/remote-mcp-smoke-client.mjs +7 -4
  102. package/src/runtime-update.mjs +100 -39
  103. package/src/skill-mcp-tools-r44.mjs +37 -0
  104. package/src/skill-plane-r44.mjs +203 -0
  105. package/src/tunnel-stdio-compat-smoke.mjs +1 -1
  106. package/src/version.mjs +1 -1
  107. package/test/agent-backend-r44.test.mjs +115 -0
  108. package/test/agent-runtime.test.mjs +4 -3
  109. package/test/autonomous-loop.test.mjs +121 -11
  110. package/test/autonomous-runtime.test.mjs +3 -2
  111. package/test/capability-ledger-r36.test.mjs +3 -3
  112. package/test/cli-entrypoint.test.mjs +4 -4
  113. package/test/codex-app-server-r44.test.mjs +115 -0
  114. package/test/codex-autonomous-r44.test.mjs +87 -0
  115. package/test/coding-plane.test.mjs +3 -2
  116. package/test/coding-runtime.test.mjs +36 -1
  117. package/test/compact-catalog-r36.test.mjs +3 -3
  118. package/test/compact-max-catalog-r40.test.mjs +4 -2
  119. package/test/compact-max-catalog-r44.test.mjs +97 -0
  120. package/test/compact-max-catalog-r45.test.mjs +99 -0
  121. package/test/contained.test.mjs +23 -11
  122. package/test/controller.test.mjs +5 -1
  123. package/test/core.test.mjs +1 -1
  124. package/test/durable-job-r44.test.mjs +75 -0
  125. package/test/external-job-provider-r44.test.mjs +46 -0
  126. package/test/full-max-catalog-r40.test.mjs +5 -3
  127. package/test/full-max-catalog-r44.test.mjs +91 -0
  128. package/test/full-max-catalog-r45.test.mjs +91 -0
  129. package/test/hardware-observation-r45.test.mjs +44 -0
  130. package/test/host-inline-r45.test.mjs +67 -0
  131. package/test/host-plane.test.mjs +15 -1
  132. package/test/machine-mcp-integration.test.mjs +1 -0
  133. package/test/native-diff.test.mjs +28 -0
  134. package/test/observation-mcp-tools.test.mjs +4 -3
  135. package/test/output-schema.test.mjs +3 -2
  136. package/test/package-boundary.test.mjs +1 -1
  137. package/test/process-policy.test.mjs +22 -1
  138. package/test/production-docs.test.mjs +3 -3
  139. package/test/prompts-resources.test.mjs +1 -1
  140. package/test/r33-closeout-regression.test.mjs +20 -36
  141. package/test/r33-finalization.test.mjs +7 -7
  142. package/test/r43-finalization.test.mjs +31 -0
  143. package/test/r43-finalizer.test.mjs +34 -0
  144. package/test/r43-parent.test.mjs +29 -0
  145. package/test/r44-finalization.test.mjs +58 -0
  146. package/test/r44-finalizer.test.mjs +48 -0
  147. package/test/r44-parent.test.mjs +25 -0
  148. package/test/r45-autonomous-quick-test.test.mjs +10 -0
  149. package/test/r45-finalization.test.mjs +84 -0
  150. package/test/release-generation.test.mjs +1 -0
  151. package/test/release-version.test.mjs +65 -20
  152. package/test/remote-device-r44.test.mjs +104 -0
  153. package/test/runtime-host-bootstrap-r45.test.mjs +46 -0
  154. package/test/runtime-self-update.test.mjs +42 -0
  155. package/test/skill-mcp-r44.test.mjs +38 -0
  156. package/test/skill-plane-r44.test.mjs +93 -0
  157. package/test/standing-grants.test.mjs +5 -1
@@ -0,0 +1,308 @@
1
+ #define WIN32_LEAN_AND_MEAN
2
+ #include <winsock2.h>
3
+ #include <ws2tcpip.h>
4
+ #include <windows.h>
5
+ #include <iphlpapi.h>
6
+ #include <setupapi.h>
7
+ #include <intrin.h>
8
+ #include <stdint.h>
9
+
10
+ #include <algorithm>
11
+ #include <array>
12
+ #include <cstring>
13
+ #include <iostream>
14
+ #include <sstream>
15
+ #include <string>
16
+ #include <vector>
17
+
18
+ #pragma comment(lib, "iphlpapi.lib")
19
+ #pragma comment(lib, "setupapi.lib")
20
+ #pragma comment(lib, "user32.lib")
21
+
22
+ static std::string utf8(const wchar_t* text) {
23
+ if (!text || !*text) return {};
24
+ const int needed = WideCharToMultiByte(CP_UTF8, WC_ERR_INVALID_CHARS, text, -1, nullptr, 0, nullptr, nullptr);
25
+ if (needed <= 1) return {};
26
+ std::string out(static_cast<size_t>(needed - 1), '\0');
27
+ if (WideCharToMultiByte(CP_UTF8, WC_ERR_INVALID_CHARS, text, -1, out.data(), needed, nullptr, nullptr) == 0) return {};
28
+ return out;
29
+ }
30
+
31
+ static std::string json_escape(const std::string& value) {
32
+ std::ostringstream out;
33
+ for (const unsigned char ch : value) {
34
+ switch (ch) {
35
+ case '"': out << "\\\""; break;
36
+ case '\\': out << "\\\\"; break;
37
+ case '\b': out << "\\b"; break;
38
+ case '\f': out << "\\f"; break;
39
+ case '\n': out << "\\n"; break;
40
+ case '\r': out << "\\r"; break;
41
+ case '\t': out << "\\t"; break;
42
+ default:
43
+ if (ch < 0x20U) {
44
+ const char hex[] = "0123456789abcdef";
45
+ out << "\\u00" << hex[(ch >> 4U) & 0x0fU] << hex[ch & 0x0fU];
46
+ } else {
47
+ out << static_cast<char>(ch);
48
+ }
49
+ }
50
+ }
51
+ return out.str();
52
+ }
53
+
54
+ static std::string quote(const std::string& value) {
55
+ return std::string("\"") + json_escape(value) + "\"";
56
+ }
57
+
58
+ static std::string trim_ascii(std::string value) {
59
+ while (!value.empty() && (value.back() == '\0' || value.back() == ' ')) value.pop_back();
60
+ size_t first = 0;
61
+ while (first < value.size() && value[first] == ' ') ++first;
62
+ return value.substr(first);
63
+ }
64
+
65
+ static std::string cpu_json() {
66
+ int regs[4] = {};
67
+ __cpuid(regs, 0);
68
+ const unsigned int max_basic = static_cast<unsigned int>(regs[0]);
69
+ std::array<char, 13> vendor{};
70
+ std::memcpy(vendor.data() + 0, &regs[1], 4);
71
+ std::memcpy(vendor.data() + 4, &regs[3], 4);
72
+ std::memcpy(vendor.data() + 8, &regs[2], 4);
73
+
74
+ __cpuid(regs, static_cast<int>(0x80000000U));
75
+ const unsigned int max_ext = static_cast<unsigned int>(regs[0]);
76
+ std::array<char, 49> brand{};
77
+ if (max_ext >= 0x80000004U) {
78
+ for (unsigned int leaf = 0; leaf < 3U; ++leaf) {
79
+ __cpuid(regs, static_cast<int>(0x80000002U + leaf));
80
+ std::memcpy(brand.data() + (leaf * 16U), regs, 16);
81
+ }
82
+ }
83
+
84
+ unsigned int family = 0U, model = 0U, stepping = 0U;
85
+ if (max_basic >= 1U) {
86
+ __cpuid(regs, 1);
87
+ const unsigned int eax = static_cast<unsigned int>(regs[0]);
88
+ stepping = eax & 0x0fU;
89
+ unsigned int base_model = (eax >> 4U) & 0x0fU;
90
+ unsigned int base_family = (eax >> 8U) & 0x0fU;
91
+ const unsigned int ext_model = (eax >> 16U) & 0x0fU;
92
+ const unsigned int ext_family = (eax >> 20U) & 0xffU;
93
+ family = base_family == 0x0fU ? base_family + ext_family : base_family;
94
+ model = (base_family == 0x06U || base_family == 0x0fU) ? (ext_model << 4U) | base_model : base_model;
95
+ }
96
+
97
+ std::ostringstream out;
98
+ out << "{\"vendor\":" << quote(vendor.data())
99
+ << ",\"brand\":" << quote(trim_ascii(brand.data()))
100
+ << ",\"family\":" << family
101
+ << ",\"model\":" << model
102
+ << ",\"stepping\":" << stepping
103
+ << ",\"logical_processors\":" << GetActiveProcessorCount(ALL_PROCESSOR_GROUPS)
104
+ << ",\"processor_groups\":" << GetActiveProcessorGroupCount()
105
+ << "}";
106
+ return out.str();
107
+ }
108
+
109
+ static std::string memory_json() {
110
+ MEMORYSTATUSEX ms{};
111
+ ms.dwLength = sizeof(ms);
112
+ if (!GlobalMemoryStatusEx(&ms)) throw std::runtime_error("GlobalMemoryStatusEx failed");
113
+ std::ostringstream out;
114
+ out << "{\"memory_load_pct\":" << ms.dwMemoryLoad
115
+ << ",\"total_physical_bytes\":" << ms.ullTotalPhys
116
+ << ",\"available_physical_bytes\":" << ms.ullAvailPhys
117
+ << ",\"total_pagefile_bytes\":" << ms.ullTotalPageFile
118
+ << ",\"available_pagefile_bytes\":" << ms.ullAvailPageFile
119
+ << ",\"total_virtual_bytes\":" << ms.ullTotalVirtual
120
+ << ",\"available_virtual_bytes\":" << ms.ullAvailVirtual
121
+ << "}";
122
+ return out.str();
123
+ }
124
+
125
+ static std::string drive_type_name(UINT type) {
126
+ switch (type) {
127
+ case DRIVE_REMOVABLE: return "removable";
128
+ case DRIVE_FIXED: return "fixed";
129
+ case DRIVE_REMOTE: return "remote";
130
+ case DRIVE_CDROM: return "cdrom";
131
+ case DRIVE_RAMDISK: return "ramdisk";
132
+ default: return "unknown";
133
+ }
134
+ }
135
+
136
+ static std::string storage_json() {
137
+ const DWORD needed = GetLogicalDriveStringsW(0, nullptr);
138
+ if (needed == 0) throw std::runtime_error("GetLogicalDriveStringsW size failed");
139
+ std::vector<wchar_t> buffer(static_cast<size_t>(needed) + 2U, L'\0');
140
+ if (GetLogicalDriveStringsW(needed + 1U, buffer.data()) == 0) throw std::runtime_error("GetLogicalDriveStringsW failed");
141
+
142
+ std::ostringstream out;
143
+ out << "{\"drives\":[";
144
+ bool first = true;
145
+ for (const wchar_t* root = buffer.data(); *root; root += wcslen(root) + 1U) {
146
+ ULARGE_INTEGER available{}, total{}, free_bytes{};
147
+ const BOOL space_ok = GetDiskFreeSpaceExW(root, &available, &total, &free_bytes);
148
+ wchar_t volume_name[MAX_PATH + 1] = {};
149
+ wchar_t filesystem[MAX_PATH + 1] = {};
150
+ DWORD serial = 0, max_component = 0, flags = 0;
151
+ const BOOL volume_ok = GetVolumeInformationW(root, volume_name, MAX_PATH, &serial, &max_component, &flags, filesystem, MAX_PATH);
152
+ if (!first) out << ',';
153
+ first = false;
154
+ out << "{\"root\":" << quote(utf8(root))
155
+ << ",\"type\":" << quote(drive_type_name(GetDriveTypeW(root)))
156
+ << ",\"volume\":" << quote(volume_ok ? utf8(volume_name) : std::string())
157
+ << ",\"filesystem\":" << quote(volume_ok ? utf8(filesystem) : std::string())
158
+ << ",\"serial\":" << (volume_ok ? serial : 0U)
159
+ << ",\"total_bytes\":" << (space_ok ? total.QuadPart : 0ULL)
160
+ << ",\"free_bytes\":" << (space_ok ? free_bytes.QuadPart : 0ULL)
161
+ << ",\"available_bytes\":" << (space_ok ? available.QuadPart : 0ULL)
162
+ << "}";
163
+ }
164
+ out << "]}";
165
+ return out.str();
166
+ }
167
+
168
+ static std::string mac_hex(const BYTE* bytes, ULONG length) {
169
+ static const char hex[] = "0123456789abcdef";
170
+ std::string out;
171
+ for (ULONG i = 0; i < length; ++i) {
172
+ if (i) out.push_back(':');
173
+ out.push_back(hex[(bytes[i] >> 4U) & 0x0fU]);
174
+ out.push_back(hex[bytes[i] & 0x0fU]);
175
+ }
176
+ return out;
177
+ }
178
+
179
+ static std::string network_json() {
180
+ ULONG size = 0;
181
+ DWORD rc = GetAdaptersAddresses(AF_UNSPEC, GAA_FLAG_INCLUDE_PREFIX, nullptr, nullptr, &size);
182
+ if (rc != ERROR_BUFFER_OVERFLOW) throw std::runtime_error("GetAdaptersAddresses size failed");
183
+ std::vector<unsigned char> storage(size);
184
+ auto* head = reinterpret_cast<IP_ADAPTER_ADDRESSES*>(storage.data());
185
+ rc = GetAdaptersAddresses(AF_UNSPEC, GAA_FLAG_INCLUDE_PREFIX, nullptr, head, &size);
186
+ if (rc != NO_ERROR) throw std::runtime_error("GetAdaptersAddresses failed");
187
+
188
+ std::ostringstream out;
189
+ out << "{\"adapters\":[";
190
+ bool first = true;
191
+ for (auto* item = head; item; item = item->Next) {
192
+ if (!first) out << ',';
193
+ first = false;
194
+ out << "{\"name\":" << quote(item->AdapterName ? item->AdapterName : "")
195
+ << ",\"friendly_name\":" << quote(utf8(item->FriendlyName))
196
+ << ",\"description\":" << quote(utf8(item->Description))
197
+ << ",\"if_index\":" << item->IfIndex
198
+ << ",\"ipv6_if_index\":" << item->Ipv6IfIndex
199
+ << ",\"mtu\":" << item->Mtu
200
+ << ",\"oper_status\":" << static_cast<unsigned long>(item->OperStatus)
201
+ << ",\"physical_address\":" << quote(mac_hex(item->PhysicalAddress, item->PhysicalAddressLength))
202
+ << "}";
203
+ }
204
+ out << "]}";
205
+ return out.str();
206
+ }
207
+
208
+ static std::string gpu_json() {
209
+ std::ostringstream out;
210
+ out << "{\"devices\":[";
211
+ bool first = true;
212
+ for (DWORD index = 0;; ++index) {
213
+ DISPLAY_DEVICEW dd{};
214
+ dd.cb = sizeof(dd);
215
+ if (!EnumDisplayDevicesW(nullptr, index, &dd, 0)) break;
216
+ if (!first) out << ',';
217
+ first = false;
218
+ out << "{\"device_name\":" << quote(utf8(dd.DeviceName))
219
+ << ",\"device_string\":" << quote(utf8(dd.DeviceString))
220
+ << ",\"device_id\":" << quote(utf8(dd.DeviceID))
221
+ << ",\"device_key\":" << quote(utf8(dd.DeviceKey))
222
+ << ",\"state_flags\":" << dd.StateFlags
223
+ << "}";
224
+ }
225
+ out << "]}";
226
+ return out.str();
227
+ }
228
+
229
+ static std::string get_device_property(HDEVINFO info, SP_DEVINFO_DATA& data, DWORD property) {
230
+ DWORD type = 0, required = 0;
231
+ SetupDiGetDeviceRegistryPropertyW(info, &data, property, &type, nullptr, 0, &required);
232
+ if (required == 0) return {};
233
+ std::vector<BYTE> bytes(required + sizeof(wchar_t), 0);
234
+ if (!SetupDiGetDeviceRegistryPropertyW(info, &data, property, &type, bytes.data(), static_cast<DWORD>(bytes.size()), nullptr)) return {};
235
+ return utf8(reinterpret_cast<const wchar_t*>(bytes.data()));
236
+ }
237
+
238
+ static std::string get_instance_id(HDEVINFO info, SP_DEVINFO_DATA& data) {
239
+ DWORD required = 0;
240
+ SetupDiGetDeviceInstanceIdW(info, &data, nullptr, 0, &required);
241
+ if (required == 0) return {};
242
+ std::vector<wchar_t> buffer(static_cast<size_t>(required) + 1U, L'\0');
243
+ if (!SetupDiGetDeviceInstanceIdW(info, &data, buffer.data(), static_cast<DWORD>(buffer.size()), nullptr)) return {};
244
+ return utf8(buffer.data());
245
+ }
246
+
247
+ static std::string pci_json() {
248
+ HDEVINFO info = SetupDiGetClassDevsW(nullptr, L"PCI", nullptr, DIGCF_ALLCLASSES | DIGCF_PRESENT);
249
+ if (info == INVALID_HANDLE_VALUE) throw std::runtime_error("SetupDiGetClassDevsW PCI failed");
250
+
251
+ std::ostringstream out;
252
+ out << "{\"devices\":[";
253
+ bool first = true;
254
+ for (DWORD index = 0;; ++index) {
255
+ SP_DEVINFO_DATA data{};
256
+ data.cbSize = sizeof(data);
257
+ if (!SetupDiEnumDeviceInfo(info, index, &data)) {
258
+ if (GetLastError() == ERROR_NO_MORE_ITEMS) break;
259
+ SetupDiDestroyDeviceInfoList(info);
260
+ throw std::runtime_error("SetupDiEnumDeviceInfo failed");
261
+ }
262
+ std::string name = get_device_property(info, data, SPDRP_FRIENDLYNAME);
263
+ if (name.empty()) name = get_device_property(info, data, SPDRP_DEVICEDESC);
264
+ const std::string hardware = get_device_property(info, data, SPDRP_HARDWAREID);
265
+ const std::string instance = get_instance_id(info, data);
266
+ if (!first) out << ',';
267
+ first = false;
268
+ out << "{\"name\":" << quote(name)
269
+ << ",\"hardware_id\":" << quote(hardware)
270
+ << ",\"instance_id\":" << quote(instance)
271
+ << "}";
272
+ }
273
+ SetupDiDestroyDeviceInfoList(info);
274
+ out << "]}";
275
+ return out.str();
276
+ }
277
+
278
+ static std::string build_data(const std::string& query) {
279
+ if (query == "cpu") return cpu_json();
280
+ if (query == "memory") return memory_json();
281
+ if (query == "storage") return storage_json();
282
+ if (query == "network") return network_json();
283
+ if (query == "gpu") return gpu_json();
284
+ if (query == "pci") return pci_json();
285
+ throw std::runtime_error("unsupported hardware query");
286
+ }
287
+
288
+ int wmain(int argc, wchar_t** argv) {
289
+ try {
290
+ if (argc == 2 && std::wstring(argv[1]) == L"--selftest") {
291
+ const std::string probe = cpu_json();
292
+ if (probe.empty()) return 3;
293
+ std::cout << "{\"status\":\"passed\",\"schema\":\"deadbyte.hardware-observer-selftest.v1\"}\n";
294
+ return 0;
295
+ }
296
+ if (argc != 2) {
297
+ std::cerr << "usage: deadbyte-hardware-observer-r45.exe <cpu|gpu|memory|storage|network|pci>\n";
298
+ return 2;
299
+ }
300
+ const std::string query = utf8(argv[1]);
301
+ const std::string data = build_data(query);
302
+ std::cout << "{\"schema\":\"deadbyte.hardware-query.v1\",\"query\":" << quote(query) << ",\"data\":" << data << "}\n";
303
+ return 0;
304
+ } catch (const std::exception& error) {
305
+ std::cerr << error.what() << '\n';
306
+ return 1;
307
+ }
308
+ }
package/package.json CHANGED
@@ -1,9 +1,9 @@
1
1
  {
2
2
  "name": "deadbyte-mcp",
3
- "version": "0.14.0",
3
+ "version": "0.15.1",
4
4
  "private": false,
5
5
  "type": "module",
6
- "description": "Authenticated MCP agentic runtime with identity-bound task contracts, typed human clarification, bounded model providers, signed audit chains, immutable release slots, and separately revocable machine authority.",
6
+ "description": "Authenticated MCP agentic runtime with signed skills, persistent model backends, identity-bound remote devices, durable job supervision, immutable release slots, and separately revocable machine authority.",
7
7
  "engines": {
8
8
  "node": ">=22"
9
9
  },
@@ -16,10 +16,10 @@
16
16
  "r42:parent:verify": "node scripts/verify-r42-parent.mjs",
17
17
  "r42:eval": "node scripts/agent-eval-r42.mjs",
18
18
  "self-update:runtime": "node scripts/runtime-self-update.mjs",
19
- "self-update:deferred": "node scripts/deferred-slot-operation-r42.mjs",
20
- "release:parity": "node scripts/release-parity-r42.mjs",
21
- "release:final:write": "node scripts/final-closure-r42.mjs",
22
- "release:final:verify": "node scripts/final-closure-verify-r42.mjs",
19
+ "self-update:deferred": "node scripts/deferred-slot-operation-r45.mjs",
20
+ "release:parity": "node scripts/release-parity-r45.mjs",
21
+ "release:final:write": "node scripts/final-closure-r45.mjs",
22
+ "release:final:verify": "node scripts/final-closure-verify-r45.mjs",
23
23
  "proof": "node src/proof-cli.mjs workspaces/demo input.txt",
24
24
  "verify": "node src/verifier-cli.mjs workspaces/demo evidence/latest.json",
25
25
  "trust:init": "node src/trust-init.mjs",
@@ -42,7 +42,7 @@
42
42
  "contained:run": "node src/contained-cli.mjs workspaces/demo input.txt",
43
43
  "contained:smoke": "node src/contained-smoke.mjs",
44
44
  "mcp:contained:smoke": "node src/mcp-contained-smoke-client.mjs",
45
- "gate:windows": "powershell -NoProfile -ExecutionPolicy Bypass -File scripts/gate-windows-r42.ps1",
45
+ "gate:windows": "powershell -NoProfile -ExecutionPolicy Bypass -File scripts/gate-windows-r45.ps1",
46
46
  "authority:smoke": "node src/authority-smoke.mjs",
47
47
  "mcp:remote:smoke": "node src/remote-mcp-smoke-client.mjs",
48
48
  "mcp:host:smoke": "node src/mcp-host-smoke-client.mjs",
@@ -53,7 +53,17 @@
53
53
  "audit:verify": "node src/deadbyte-cli.mjs audit verify",
54
54
  "audit:status": "node src/deadbyte-cli.mjs audit status",
55
55
  "desktop:build": "powershell -NoProfile -ExecutionPolicy Bypass -File scripts/build-desktop-r40.ps1",
56
- "desktop:policy:refresh": "powershell -NoProfile -ExecutionPolicy Bypass -File scripts/init-desktop-policy-r40.ps1"
56
+ "desktop:policy:refresh": "powershell -NoProfile -ExecutionPolicy Bypass -File scripts/init-desktop-policy-r40.ps1",
57
+ "r43:parent:verify": "node scripts/verify-r43-parent.mjs",
58
+ "r43:full:test": "node scripts/full-regression-r43.mjs",
59
+ "r44:parent:verify": "node scripts/verify-r44-parent.mjs",
60
+ "r44:full:test": "node scripts/full-regression-r44.mjs",
61
+ "finalize:r44": "node scripts/finalize-r44.mjs",
62
+ "hardware:build": "powershell -NoProfile -ExecutionPolicy Bypass -File scripts/build-hardware-r45.ps1",
63
+ "doctor": "node src/deadbyte-cli.mjs doctor",
64
+ "r45:parent:verify": "node scripts/verify-r45-parent.mjs",
65
+ "r45:full:test": "node scripts/full-regression-r45.mjs",
66
+ "finalize:r45": "node scripts/finalize-r45.mjs"
57
67
  },
58
68
  "bundleDependencies": [
59
69
  "@modelcontextprotocol/server",
@@ -3,7 +3,7 @@ Set-StrictMode -Version 2.0
3
3
  $root = Split-Path -Parent $PSScriptRoot
4
4
  Push-Location $root
5
5
  try {
6
- & npm.cmd test
7
- if ($LASTEXITCODE -ne 0) { throw "npm test failed with exit code $LASTEXITCODE" }
6
+ & node.exe --test test/autonomous-live-fixture.test.mjs
7
+ if ($LASTEXITCODE -ne 0) { throw "autonomous fixture test failed with exit code $LASTEXITCODE" }
8
8
  Write-Output 'R24 QUICK TEST PASS'
9
9
  } finally { Pop-Location }
@@ -0,0 +1,71 @@
1
+ $ErrorActionPreference='Stop'
2
+ Set-StrictMode -Version Latest
3
+
4
+ function Get-Sha256Hex {
5
+ param([Parameter(Mandatory=$true)][string]$Path)
6
+ $Stream=[System.IO.File]::OpenRead([System.IO.Path]::GetFullPath($Path))
7
+ try {
8
+ $Hasher=[System.Security.Cryptography.SHA256]::Create()
9
+ try { return ([System.BitConverter]::ToString($Hasher.ComputeHash($Stream))).Replace('-','').ToLowerInvariant() }
10
+ finally { $Hasher.Dispose() }
11
+ } finally { $Stream.Dispose() }
12
+ }
13
+
14
+ $Root=Split-Path -Parent $PSScriptRoot
15
+ $Src=Join-Path $Root 'native\deadbyte-hardware-observer.cpp'
16
+ $Bin=Join-Path $Root 'bin'
17
+ $Exe=Join-Path $Bin 'deadbyte-hardware-observer-r45.exe'
18
+ $Obj=Join-Path $Bin 'deadbyte-hardware-observer-r45.obj'
19
+ New-Item -ItemType Directory -Force -Path $Bin | Out-Null
20
+
21
+ $vswhere='C:\Program Files (x86)\Microsoft Visual Studio\Installer\vswhere.exe'
22
+ if(-not (Test-Path -LiteralPath $vswhere)){throw 'vswhere.exe not found'}
23
+ $install=(& $vswhere -latest -products * -requires Microsoft.VisualStudio.Component.VC.Tools.x86.x64 -property installationPath | Select-Object -First 1)
24
+ if(-not $install){throw 'MSVC x64 C++ toolchain not found'}
25
+ $dev=Join-Path $install 'Common7\Tools\VsDevCmd.bat'
26
+ if(-not (Test-Path -LiteralPath $dev)){throw "VsDevCmd.bat missing: $dev"}
27
+ $cmd=if($env:ComSpec){$env:ComSpec}else{Join-Path $env:SystemRoot 'System32\cmd.exe'}
28
+
29
+ Remove-Item -Force -ErrorAction SilentlyContinue $Exe,$Obj
30
+ $common='/nologo /std:c++17 /permissive- /W4 /WX /O2 /MT /EHsc /guard:cf /diagnostics:caret /FC /utf-8 /Brepro /DUNICODE /D_UNICODE /D_WIN32_WINNT=0x0A00 /DWINVER=0x0A00'
31
+ $compile='cl {0} "{1}" /Fo:"{2}" /Fe:"{3}" iphlpapi.lib setupapi.lib user32.lib /link /Brepro /INCREMENTAL:NO' -f $common,$Src,$Obj,$Exe
32
+ $line='call "{0}" -no_logo -arch=x64 -host_arch=x64 && {1}' -f $dev,$compile
33
+ $out=& $cmd /d /s /c $line 2>&1
34
+ $exit=$LASTEXITCODE
35
+ $out | ForEach-Object { Write-Host ([string]$_) }
36
+ if($exit -ne 0){throw "hardware observer compile failed exit=$exit"}
37
+ if(-not (Test-Path -LiteralPath $Exe -PathType Leaf)){throw 'hardware observer exe missing after compile'}
38
+
39
+ $self=& $Exe --selftest 2>&1
40
+ $selfExit=$LASTEXITCODE
41
+ $self | ForEach-Object { Write-Host ([string]$_) }
42
+ if($selfExit -ne 0){throw "hardware observer selftest failed exit=$selfExit"}
43
+ if(-not (($self -join [Environment]::NewLine) -match '"status":"passed"')){throw 'hardware observer selftest did not report pass'}
44
+
45
+ $queries=[ordered]@{}
46
+ foreach($query in @('cpu','gpu','memory','storage','network','pci')){
47
+ $raw=& $Exe $query 2>&1
48
+ $queryExit=$LASTEXITCODE
49
+ if($queryExit -ne 0){throw "hardware query $query failed exit=$queryExit output=$($raw -join ' ')"}
50
+ $text=($raw -join [Environment]::NewLine)
51
+ $parsed=$text | ConvertFrom-Json
52
+ if($parsed.schema -ne 'deadbyte.hardware-query.v1' -or $parsed.query -ne $query){throw "hardware query $query contract mismatch"}
53
+ $queries[$query]=Get-Sha256Hex -Path $Exe
54
+ }
55
+
56
+ $depLine='call "{0}" -no_logo -arch=x64 -host_arch=x64 && dumpbin /nologo /dependents "{1}"' -f $dev,$Exe
57
+ $deps=& $cmd /d /s /c $depLine 2>&1
58
+ $depExit=$LASTEXITCODE
59
+ $deps | ForEach-Object { Write-Host ([string]$_) }
60
+ if($depExit -ne 0){throw "hardware observer dumpbin failed exit=$depExit"}
61
+
62
+ [pscustomobject]@{
63
+ status='built'
64
+ source_sha256=Get-Sha256Hex -Path $Src
65
+ exe=$Exe
66
+ exe_sha256=Get-Sha256Hex -Path $Exe
67
+ obj_sha256=Get-Sha256Hex -Path $Obj
68
+ selftest=@($self | ForEach-Object {[string]$_})
69
+ queries=@($queries.Keys)
70
+ dependencies=@($deps | ForEach-Object {[string]$_})
71
+ }|ConvertTo-Json -Depth 5
@@ -0,0 +1,126 @@
1
+ import { createHash, createPublicKey, randomBytes } from 'node:crypto';
2
+ import { spawn } from 'node:child_process';
3
+ import { mkdir, readFile, realpath, writeFile } from 'node:fs/promises';
4
+ import os from 'node:os';
5
+ import path from 'node:path';
6
+ import { fileURLToPath } from 'node:url';
7
+ import { parseActivePointer } from '../src/release-slot.mjs';
8
+ import { loadPowerShellDataFile, runSlotUpdateCli, verifySlotUpdateEnvelope } from '../src/runtime-update.mjs';
9
+
10
+ const HEX64=/^[0-9a-f]{64}$/;
11
+ const RECEIPT_ID=/^r27-[A-Za-z0-9-]+$/;
12
+ const here=path.dirname(fileURLToPath(import.meta.url));
13
+ const packageRoot=path.resolve(here,'..');
14
+ const stateRoot=path.resolve(process.env.DEADBYTE_STATE_ROOT||path.join(os.homedir(),'.deadbyte-mcp'));
15
+ const evidenceRoot=path.join(stateRoot,'evidence','deferred-slot-operations');
16
+ const sha256=bytes=>createHash('sha256').update(bytes).digest('hex');
17
+ const atomicJson=async(file,value)=>{
18
+ await mkdir(path.dirname(file),{recursive:true});
19
+ const temp=`${file}.${process.pid}.${randomBytes(4).toString('hex')}.tmp`;
20
+ await writeFile(temp,`${JSON.stringify(value,null,2)}\n`,{flag:'wx'});
21
+ await import('node:fs/promises').then(fs=>fs.rename(temp,file));
22
+ };
23
+ function activationArgs(manifestSha){
24
+ if(!HEX64.test(manifestSha??'')) throw new Error('activate requires one lowercase manifest SHA-256');
25
+ return ['--stage',packageRoot,'--development-root',packageRoot,'--expected-version','0.14.1',
26
+ '--expected-manifest',manifestSha,'--process-policy',path.join(packageRoot,'controller','deadbyte-process-policy.json'),
27
+ '--process-policy-sha256',null,'--desktop-policy',path.join(packageRoot,'controller','deadbyte-desktop-policy.json'),
28
+ '--desktop-policy-sha256',null,'--semantic-lsp-config',path.join(packageRoot,'controller','deadbyte-semantic-lsp-config.json'),
29
+ '--semantic-lsp-config-sha256',null,'--enable-machine-fs','--enable-observation','--enable-desktop','--enable-autonomous-supervisor'];
30
+ }
31
+ async function bridgeBootstrapArgs(explicitBridgeRoot=null,explicitBridgeSha256=null){
32
+ const hasRoot=typeof explicitBridgeRoot==='string'&&explicitBridgeRoot.length>0;
33
+ const hasSha=typeof explicitBridgeSha256==='string'&&explicitBridgeSha256.length>0;
34
+ if(hasRoot!==hasSha) throw new Error('bridge override requires exact root + SHA pair');
35
+ let bridgeRootRaw,expectedSha256=null;
36
+ if(hasRoot){
37
+ if(!path.isAbsolute(explicitBridgeRoot)||!HEX64.test(explicitBridgeSha256)) throw new Error('bridge override requires exact root + SHA pair');
38
+ bridgeRootRaw=explicitBridgeRoot;expectedSha256=explicitBridgeSha256;
39
+ }else{
40
+ const pointer=parseActivePointer(await readFile(path.join(stateRoot,'active-release.json'),'utf8'));
41
+ const config=await loadPowerShellDataFile(pointer.config_path);
42
+ bridgeRootRaw=config?.Bridge?.WorkingDirectory;
43
+ if(typeof bridgeRootRaw!=='string'||!path.isAbsolute(bridgeRootRaw)) throw new Error('active controller Bridge.WorkingDirectory must be absolute');
44
+ }
45
+ const bridgeRoot=await realpath(path.resolve(bridgeRootRaw));
46
+ const packageFile=path.join(bridgeRoot,'package.json');
47
+ const bridgeScript=path.join(bridgeRoot,'src','bridge.mjs');
48
+ const pkg=JSON.parse(await readFile(packageFile,'utf8'));
49
+ if(pkg?.name!=='deadbyte-chatgpt-bridge') throw new Error('active Bridge package identity mismatch');
50
+ const scriptSha256=sha256(await readFile(bridgeScript));
51
+ if(expectedSha256&&scriptSha256!==expectedSha256) throw new Error('bridge override SHA-256 mismatch');
52
+ return ['--bridge-root',bridgeRoot,'--bridge-script-sha256',scriptSha256];
53
+ }
54
+ async function rollbackArgs(receiptPath){
55
+ const resolved=await realpath(path.resolve(receiptPath));
56
+ const allowed=path.join(stateRoot,'evidence','updates')+path.sep;
57
+ if(!resolved.startsWith(allowed)||path.basename(resolved).toLowerCase()!=='receipt.json'||!RECEIPT_ID.test(path.basename(path.dirname(resolved)))) {
58
+ throw new Error('rollback receipt must be one signed activation receipt under the update evidence store');
59
+ }
60
+ const envelope=JSON.parse(await readFile(resolved,'utf8'));
61
+ const publicKey=createPublicKey(await readFile(path.join(stateRoot,'trust','ed25519-public.pem')));
62
+ if(!verifySlotUpdateEnvelope(envelope,publicKey)||envelope.body?.rollback_performed!==false) throw new Error('rollback activation receipt verification failed');
63
+ const pointer=parseActivePointer(await readFile(path.join(stateRoot,'active-release.json'),'utf8'));
64
+ if(pointer.release_id!==envelope.body?.active_pointer?.release_id||pointer.generation_root!==envelope.body?.active_pointer?.generation_root) {
65
+ throw new Error('rollback receipt does not identify the active release generation');
66
+ }
67
+ return ['--rollback-receipt',resolved];
68
+ }
69
+ async function normalizedArgs(mode,value,{explicitBridgeRoot=null,explicitBridgeSha256=null}={}){
70
+ if(mode==='activate'){
71
+ const args=activationArgs(value);
72
+ args[args.indexOf('--process-policy-sha256')+1]=sha256(await readFile(path.join(packageRoot,'controller','deadbyte-process-policy.json')));
73
+ args[args.indexOf('--desktop-policy-sha256')+1]=sha256(await readFile(path.join(packageRoot,'controller','deadbyte-desktop-policy.json')));
74
+ args[args.indexOf('--semantic-lsp-config-sha256')+1]=sha256(await readFile(path.join(packageRoot,'controller','deadbyte-semantic-lsp-config.json')));
75
+ args.push(...await bridgeBootstrapArgs(explicitBridgeRoot,explicitBridgeSha256));
76
+ return args;
77
+ }
78
+ if(mode==='rollback'){
79
+ if(explicitBridgeRoot||explicitBridgeSha256) throw new Error('rollback does not accept bridge override');
80
+ return rollbackArgs(value);
81
+ }
82
+ throw new Error("operation must be exactly 'activate' or 'rollback'");
83
+ }
84
+ const rawArgs=process.argv.slice(2);
85
+ const mode=rawArgs[0],value=rawArgs[1];
86
+ if(!value||!['activate','rollback'].includes(mode)) throw new Error('usage: deferred-slot-operation-r43.mjs <activate manifest_sha256|rollback activation_receipt> [--bridge-root ABS --bridge-script-sha256 HEX64]');
87
+ let cursor=2,explicitBridgeRoot=null,explicitBridgeSha256=null;
88
+ if(rawArgs[cursor]==='--bridge-root'){
89
+ explicitBridgeRoot=rawArgs[cursor+1]??null;
90
+ if(rawArgs[cursor+2]!=='--bridge-script-sha256') throw new Error('bridge override requires exact root + SHA pair');
91
+ explicitBridgeSha256=rawArgs[cursor+3]??null;cursor+=4;
92
+ }
93
+ let workerFlag=null,operationIdArg=null;
94
+ if(rawArgs[cursor]==='--worker'){workerFlag='--worker';operationIdArg=rawArgs[cursor+1]??null;cursor+=2;}
95
+ if(cursor!==rawArgs.length) throw new Error('deferred slot operation arguments invalid');
96
+ if((explicitBridgeRoot===null)!==(explicitBridgeSha256===null)) throw new Error('bridge override requires exact root + SHA pair');
97
+ if(mode==='rollback'&&(explicitBridgeRoot||explicitBridgeSha256)) throw new Error('rollback does not accept bridge override');
98
+ if(workerFlag==='--worker'){
99
+ if(!/^[0-9a-f]{32}$/.test(operationIdArg??'')) throw new Error('deferred worker operation id invalid');
100
+ const statePath=path.join(evidenceRoot,`${operationIdArg}.json`);
101
+ await new Promise(resolve=>setTimeout(resolve,4000));
102
+ await atomicJson(statePath,{schema:'deadbyte.deferred-slot-operation.v1',operation_id:operationIdArg,mode,state:'running',started_at_utc:new Date().toISOString(),bridge_root:explicitBridgeRoot,bridge_script_sha256:explicitBridgeSha256});
103
+ try{
104
+ const args=await normalizedArgs(mode,value,{explicitBridgeRoot,explicitBridgeSha256});
105
+ const result=await runSlotUpdateCli(args,{stateRoot});
106
+ await atomicJson(statePath,{schema:'deadbyte.deferred-slot-operation.v1',operation_id:operationIdArg,mode,state:'completed',
107
+ completed_at_utc:new Date().toISOString(),receipt_path:result.receipt_path,receipt_sha256:result.receipt_sha256,
108
+ active_release:result.pointer.release_id,generation_root:result.pointer.generation_root,bridge_root:explicitBridgeRoot,bridge_script_sha256:explicitBridgeSha256});
109
+ }catch(error){
110
+ await atomicJson(statePath,{schema:'deadbyte.deferred-slot-operation.v1',operation_id:operationIdArg,mode,state:'failed',
111
+ completed_at_utc:new Date().toISOString(),error:String(error?.message??error),bridge_root:explicitBridgeRoot,bridge_script_sha256:explicitBridgeSha256});
112
+ process.exitCode=1;
113
+ }
114
+ }else{
115
+ const operationId=randomBytes(16).toString('hex');
116
+ const statePath=path.join(evidenceRoot,`${operationId}.json`);
117
+ await atomicJson(statePath,{schema:'deadbyte.deferred-slot-operation.v1',operation_id:operationId,mode,state:'scheduled',scheduled_at_utc:new Date().toISOString(),bridge_root:explicitBridgeRoot,bridge_script_sha256:explicitBridgeSha256});
118
+ const workerArgs=[fileURLToPath(import.meta.url),mode,value];
119
+ if(explicitBridgeRoot) workerArgs.push('--bridge-root',explicitBridgeRoot,'--bridge-script-sha256',explicitBridgeSha256);
120
+ workerArgs.push('--worker',operationId);
121
+ const child=spawn(process.execPath,workerArgs,{
122
+ cwd:packageRoot,detached:true,stdio:'ignore',windowsHide:true,env:{...process.env,DEADBYTE_STATE_ROOT:stateRoot}
123
+ });
124
+ child.unref();
125
+ console.log(JSON.stringify({status:'scheduled',operation_id:operationId,mode,state_path:statePath,execution_provider:'deadbyte_mcp',rdc_operation_count:0,bridge_root:explicitBridgeRoot,bridge_script_sha256:explicitBridgeSha256}));
126
+ }