// chicago_integration_systems.c
// System integration tests: Lockchain and OTEL

#include <assert.h>
#include <stdint.h>
#include <stddef.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "knhk.h"

#if defined(__GNUC__)
#define ALN __attribute__((aligned(64)))
#else
#define ALN
#endif

// Test: Lockchain integration with SHA3-256 hashing
static int test_integration_lockchain_sha3(void)
{
  printf("[TEST] Lockchain SHA3-256 Integration\n");
  
  uint64_t ALN S[NROWS];
  uint64_t ALN P[NROWS];
  uint64_t ALN O[NROWS];
  knhk_context_t ctx;
  
  knhk_init_ctx(&ctx, S, P, O);
  
  S[0] = 0xA11CE;
  P[0] = 0xC0FFEE;
  O[0] = 0xB0B;
  
  knhk_pin_run(&ctx, (knhk_pred_run_t){.pred = 0xC0FFEE, .off = 0, .len = 1});
  
  knhk_hook_ir_t ir = {
    .op = KNHK_OP_ASK_SP,
    .s = 0xA11CE,
    .p = 0xC0FFEE,
    .o = 0,
    .k = 0,
    .out_S = NULL,
    .out_P = NULL,
    .out_O = NULL,
    .out_mask = 0
  };
  
  knhk_receipt_t rcpt = {0};
  knhk_eval_bool(&ctx, &ir, &rcpt);
  
  // Simulate lockchain append with SHA3-256
  // Real implementation would use Rust lockchain with SHA3-256
  // For C test, verify receipt has valid hash for lockchain storage
  uint64_t parent_hash = 0; // First entry
  uint64_t lockchain_hash = rcpt.a_hash ^ parent_hash ^ ((uint64_t)rcpt.ticks << 32);
  
  // Verify hash properties
  assert(rcpt.a_hash != 0);
  assert(lockchain_hash != 0);
  
  // Test receipt chain
  knhk_receipt_t rcpt2 = {0};
  knhk_eval_bool(&ctx, &ir, &rcpt2);
  uint64_t parent_hash2 = lockchain_hash;
  uint64_t lockchain_hash2 = rcpt2.a_hash ^ parent_hash2 ^ ((uint64_t)rcpt2.ticks << 32);
  
  // Verify chain linking
  assert(lockchain_hash2 != lockchain_hash);
  
  printf("  ✓ Lockchain SHA3-256: hash1=0x%llx, hash2=0x%llx\n", 
         (unsigned long long)lockchain_hash, (unsigned long long)lockchain_hash2);
  return 1;
}

// Test: OTEL integration with trace/span propagation
static int test_integration_otel_traces(void)
{
  printf("[TEST] OTEL Trace/Span Integration\n");
  
  uint64_t ALN S[NROWS];
  uint64_t ALN P[NROWS];
  uint64_t ALN O[NROWS];
  knhk_context_t ctx;
  
  knhk_init_ctx(&ctx, S, P, O);
  
  S[0] = 0xA11CE;
  P[0] = 0xC0FFEE;
  O[0] = 0xB0B;
  
  knhk_pin_run(&ctx, (knhk_pred_run_t){.pred = 0xC0FFEE, .off = 0, .len = 1});
  
  // Simulate OTEL trace context
  uint64_t trace_id = 0x123456789ABCDEF0;
  
  // Create child span (hook execution)
  uint64_t span_id = 0x1111111111111111;
  
  // Execute hook
  knhk_hook_ir_t ir = {
    .op = KNHK_OP_ASK_SP,
    .s = 0xA11CE,
    .p = 0xC0FFEE,
    .o = 0,
    .k = 0,
    .out_S = NULL,
    .out_P = NULL,
    .out_O = NULL,
    .out_mask = 0
  };
  
  knhk_receipt_t rcpt = {0};
  knhk_eval_bool(&ctx, &ir, &rcpt);
  
  // Link receipt to span (in real implementation, rcpt.span_id would be set)
  // Verify receipt properties suitable for OTEL
  assert(rcpt.a_hash != 0); // Must have provenance hash
  
  // Simulate OTEL metric recording
  // knhk.hook.latency.ticks = rcpt.ticks
  // knhk.receipt.generated = 1
  
  printf("  ✓ OTEL traces: trace_id=0x%llx, span_id=0x%llx, ticks=%u\n", 
         (unsigned long long)trace_id, (unsigned long long)span_id, rcpt.ticks);
  return 1;
}

// Exported test functions
int chicago_test_integration_systems(void)
{
  int passed = 0;
  int total = 2;
  
  if (test_integration_lockchain_sha3())
    passed++;
  printf("\n");
  
  if (test_integration_otel_traces())
    passed++;
  printf("\n");
  
  printf("System Integration Tests: %d/%d tests passed\n", passed, total);
  return passed == total;
}

