{"slug": "gorgon-halo-arrives-in-gmktek-do-you-need-192gb-of-lpddr5", "title": "Gorgon Halo Arrives in gmkTek.. do you need 192gb of LPDDR5?!?", "summary": "A first-look test of GMKtec's Gorgon Halo unified-memory mini-PC compared it against an Nvidia-based Spark system, with 184 GiB usable versus 121 GiB usable, serving the same models across engines including vLLM 0.32.0+strix, llama.cpp build 11870 (commit 74bca3950), halogen-server 0.1.4 and ds4. The two machines split results: one box won on dense models and the other on sparse ones, and the tester said some of the gap could be explained but not all of it. GMKtec is selling the Gorgon Halo through its official store and Amazon US in 2TB and 4TB configurations with discount code EVOX5PRO, $100 off at the official store and 5% off on Amazon US.", "body_md": "# \n\nThis is the first Gorgon Halo box that I get to play with! Faster memory, and 50% more of it; what’s not to love? ( aside from the price )\n\nTODO VIDEO HERE\n\n## \n\nGMKtec Official Store:\n\nAmazon US - 2TB\n\nAmazon US - 4TB\n\nDiscount Code: EVOX5PRO\n\nOfficial Store: $100 OFF\n\nAmazon US: 5% OFF\n\n# \n\n# \n\nTwo unified-memory machines, one 184 GiB (usable) and one 121 GiB (usable), asked to serve the same models. Well it turns out that’s more complicated than it would appear.\n\nOne box wins on a dense model, the other on a sparse one; it seems like I can explain some of that split, but some of it? Not so much…\n\n| Platform | Engine | Model | Mode | Plotted | Not measured | Excluded or quarantined | Qualified | \n| AMD | ds4 | deepseek-v4.1-flash | PP | 3 / 7 | 1024, 4096, 16384, 32768 | none | 3 single-run | \n| AMD | ds4 | deepseek-v4.1-flash | TG | 0 / 6 | 1024, 2048, 4096, 8192, 16384 | none | clean | \n| AMD | halogen | halogen-qwen3.8-27b | PP | 7 / 7 | none | none | clean | \n| AMD | halogen | halogen-qwen3.8-27b | TG | 6 / 6 | none | none | 5 stopped short; 2 single-run | \n| AMD | halogen-flash-server | halogen-qwen3.8-flash-next | PP | 7 / 7 | none | none | 1 single-run | \n| AMD | halogen-flash-server | halogen-qwen3.8-flash-next | TG | 0 / 6 | 512, 1024, 2048, 4096, 8192, 16384 | none | clean | \n| AMD | llamacpp | glm-5.3-flash-q5k-iq3s | PP | 7 / 7 | none | none | clean | \n| AMD | llamacpp | glm-5.3-flash-q5k-iq3s | TG | 6 / 6 | none | none | 2 single-run | \n| AMD | llamacpp | qwen3.8-27b-q4km | PP | 7 / 7 | none | none | 1 single-run | \n| AMD | llamacpp | qwen3.8-27b-q4km | TG | 6 / 6 | none | none | 2 single-run | \n| AMD | vllm | Qwen3.8-27B-AWQ-INT4 | PP | 7 / 7 | none | none | 1 single-run | \n| AMD | vllm | Qwen3.8-27B-AWQ-INT4 | TG | 3 / 6 | 4096, 8192, 16384 | none | clean | \n| Spark | ds4 | deepseek-v4.1-flash | PP | 4 / 7 | 1024, 4096, 16384 | none | 4 single-run | \n| Spark | ds4 | deepseek-v4.1-flash | TG | 0 / 6 | 1024, 2048, 4096, 8192, 16384 | none | clean | \n| Spark | llama.cpp | qwen3.8-flash-next-ud-q4kxl | PP | 7 / 7 | none | none | clean | \n| Spark | llama.cpp | qwen3.8-flash-next-ud-q4kxl | TG | 2 / 6 | 2048, 4096, 8192, 16384 | none | clean | \n| Spark | maya | glm-5.3-flash | PP | 7 / 7 | none | none | 1 checkpoint-assisted | \n| Spark | maya | glm-5.3-flash | TG | 3 / 6 | none | 4096, 8192, 16384 | clean | \n| Spark | vllm | Qwen3.8-27B-AWQ-INT4 | PP | 7 / 7 | none | none | 1 single-run | \n| Spark | vllm | Qwen3.8-27B-AWQ-INT4 | TG | 3 / 6 | 4096, 8192, 16384 | none | clean | \n| Spark | vllm | Qwen3.8-27B-NVFP4 | PP | 7 / 7 | none | none | clean | \n| Spark | vllm | Qwen3.8-27B-NVFP4 | TG | 6 / 6 | none | none | 2 single-run | \n| Spark | vllm-c4 | Qwen3.8-27B-NVFP4 | PP | 0 / 7 | 512, 1024, 2048, 4096, 8192, 16384, 32768 | none | clean | \n| Spark | vllm-c4 | Qwen3.8-27B-NVFP4 | TG | 1 / 6 | 1024, 2048, 4096, 8192, 16384 | none | clean | \n| AMD | cpukit + codecs | CPU: pcore-4 | single | 12 / 12 | none | none | clean | \n| AMD | cpukit + codecs | CPU: all-nosmt | all | 12 / 12 | none | none | clean | \n| AMD | cpukit + codecs | CPU: all-smt | all | 12 / 12 | none | none | clean | \n| Spark | cpukit + codecs | CPU: pcore-19 | single | 12 / 12 | none | none | clean | \n| Spark | cpukit + codecs | CPU: ecore-4 | single | 12 / 12 | none | none | clean | \n| Spark | cpukit + codecs | CPU: all | all | 12 / 12 | none | none | clean | \n\n ### \n\n| Platform | Engine | Version | Licence | Port | Image | \n| AMD | halogen-server | 0.1.4 | closed source | 8731 | `ghcr.io/peonist-ai/halogen:0.1.4` | \n| AMD | halogen-flash-server | 0.18.17 | closed source | 8731 | `ghcr.io/peonist-ai/halogen-flash-server:latest` | \n| AMD | vLLM | 0.32.0+strix | open source | 8000 | `kyuz0/vllm-therock-gfx1151:latest` | \n| AMD | llama.cpp | build 11870, commit 74bca3950 | open source | 8732 | `kyuz0/amd-strix-halo-toolboxes:rocm-10.0` | \n| Spark | vLLM | 0.26.1rc1.dev1219+g46638857f | open source | 8000 | `vllm/vllm-openai:nightly-46638857fdbb30e0c232c9e8f9cb1ff6d6f545c3` | \n| Spark | project-maya | v1.1.34 | open source | 8080 | `source build, github.com/mw00/project-maya` | \n\n ## \n\nA clean hardware A/B test generally requires the same software on both boxes with the same artifact. For most of this campaign I just couldn’t do that, and no amount of protocol discipline really keeps things apples-to-apples. The two AMD Halogen engine builds are closed source and run only on AMD hardware. vLLM is the Spark path (but that’s also not the only path on Spark, either). Ds4 exists on both boxes and is the only clean-ish cross-platform control we have. So most of what follows is an engine comparison that happens to run on two different pieces of hardware…\n\nvLLM runs on both boxes, but even that’s a bit fuzzy because the two boxes ran different vLLM builds (0.32.0+strix against 0.26.1rc1), different native 4-bit kernels, and different attention paths.\n\nOh, and there’s an out-of-tree patch for vLLM I mentioned in the video that shores up Spark’s problems on Qwen 3.8 flash next…\n\nCold cache is usually useful for measuring the cost of prefill, but I don’t like it for because it’s not what a chat user is going to feel at a small scale because chat users in local AI contexts are generally going to have warm prefixes. I think this might be okay as a measure of what the machine can do, though.\n\n### \n\n| Confound | Why it matters | Mitigation actually adopted | \n| No common engine | An engine win cannot be attributed to the hardware. | Only identical-artifact comparisons are treated as platform signals, and even those are qualified: the two ds4 runs use one source tree but different backends (ROCm against CUDA), so that control narrows the software difference rather than eliminating it. Every other segment is labelled as an engine comparison. | \n| Quantization density | Fewer bits per weight means fewer bytes moved per token, which changes decode speed independently of the hardware. | Qwen3.8-27B was matched at decode density and is the lead comparison. GLM-5.3-Flash could not be matched and is labelled as not like-for-like. | \n| Speculative decoding | A drafter inflates decode throughput by design and is not comparable to a non-speculative engine. | The AMD Qwen series was pinned to the serial drafter path. The speculative paths are reported separately, as a gain over serial. | \n| Prefix cache | A cache hit makes prefill look faster than the machine can compute it. | Every request carries a unique nonce prefix. Points that still showed a cache signature were quarantined by the loader. | \n| Context window | A larger n_ctx costs memory and can change prefill cost. | The ladder runs at one context per series; the context sweep is a separate experiment with its own key space. | \n| Chat versus completion endpoint | project-maya has no /v1/completions endpoint, so its numbers come from a different API surface than the others. | Disclosed. Not much to be done about this… | \n\n ## \n\nThe Qwen3.8-27B segment is the closest thing this review has to a controlled comparison. Same base model on both boxes, and – after we parsed the containers rather than trusting the file sizes – a decode-time byte cost of 1.07x. That is close enough to call matched. It still is not a hardware A/B, because the engines differ and there is no way around that. But when the artifacts are this close, and both machines land near their own cited memory-bandwidth ceilings, the numbers describe the two platform stacks more than they describe any one engine’s tuning – while still being a property of silicon and software together, not of silicon alone.\n\nThe byte cost at decode is 1.07x, not 1.64x.\n\n| Quantity | AMD halogen .hgn | Spark NVFP4 | \n| Repository | `peonist-ai/halogen-qwen3.8-27b` | `nvidia/Qwen3.8-27B-NVFP4` | \n| Quantization | w4a4/fp8r/i4l mixed | ModelOpt mixed: NVFP4 on MLP and lm_head, FP8 on linear attention, rest BF16 | \n| On disk | 33.40 GiB (35.87 GB) | 20.42 GiB (21.92 GB) | \n| Prefill-only duplicate | 12.35 GB of `.i4l` planes, read at prefill, not at decode | none | \n| Decode-resident | 21.8971 GiB (23.51 GB) | 20.4159 GiB | \n| Decode density | 6.3228 bpw over 29.7485B logical parameters | no equivalent decode-resident figure recorded | \n| Bits per weight, text model | 6.4386 | 5.9936 | \n| On-disk ratio | 1.64x | 1.00x | \n| Decode byte ratio | 1.07x | 1.00x | \n\n ### \n\n**Figure 2.** Decode against generation depth, all five series. Quantization: NVFP4-modelopt-mixed (Spark vLLM); w4a4/fp8r/i4l mixed 33.40 GiB .hgn (AMD halogen); Q4_K_M at 5.10 bpw (AMD llama.cpp); Maya-S-v2-IQ2_XXS (Spark); Q5K-IQ3S 143.54 GiB GGUF (AMD llama.cpp). Cache: cold, unique nonce prefix per request. The AMD halogen points are drawn as markers, not a line, because five of six stopped short of their requested length and sit at the depths they actually reached. A hollow ring marks a single run. The three Qwen3.8-27B series are nearly coincident, which is the decode half of the three-engine finding: engine choice barely moves a bandwidth-bound rate. Coverage is not uniform: four of the five series carry all six decode depths, but Spark project-maya has only three of six (512, 1024, 2048), because its 4096, 8192 and 16384 runs stopped short and were excluded.\n\n| pp (tokens) | AMD (halogen) | Spark (vllm) | \n| 512 | 668.51 ± 0.64 | 1978.52 ± 13.13 | \n| 1024 | 683.53 ± 9.00 | 2017.32 ± 17.89 | \n| 2048 | 670.18 ± 1.29 | 2383.97 ± 9.64 | \n| 4096 | 662.73 ± 1.82 | 2346.93 ± 10.17 | \n| 8192 | 645.90 ± 0.74 | 2363.43 ± 13.38 | \n| 16384 | 610.42 ± 0.41 | 2294.55 ± 11.85 | \n| 32768 | 550.08 ± 0.54 | 2089.52 ± 5.76 | \n\n \n| tg (tokens) | AMD (halogen) | Spark (vllm) | \n| 512 | 10.49 ± 0.00 | 12.38 ± 0.01 | \n| 1024 | 10.63 ± 0.08 | 12.31 ± 0.15 | \n| 2048 | 10.71 ± 0.03 | 12.61 ± 0.01 | \n| 4096 | 10.61 ± 0.13 | 12.54 ± 0.02 | \n| 8192 | 10.46; n=1 | 12.15; n=1 | \n| 16384 | 10.57; n=1 | 12.23; n=1 | \n\n \nQwen3.8-27B prefill at matched depth, one column per engine. Quantization: w4a4/fp8r/i4l mixed 33.40 GiB .hgn (AMD halogen); Q4_K_M at 5.10 bpw (AMD llama.cpp); NVFP4-modelopt-mixed (Spark vLLM). Cache: cold, unique nonce prefix per request. The two AMD columns are the same box and the same base model through two engines, so the gap between them is software. All three datasets descend from the same donor, so this is an engine comparison not precision.\n\nQwen3.8-27B decode at matched depth, one column per engine. Quantization: w4a4/fp8r/i4l mixed 33.40 GiB .hgn (AMD halogen); Q4_K_M at 5.10 bpw (AMD llama.cpp); NVFP4-modelopt-mixed (Spark vLLM). Cache: cold, unique nonce prefix per request. Only depth 512 is common to all three columns: five of halogen’s six decode points stopped short and are drawn at the depths they actually reached, which do not coincide with the other two ladders. The three AMD rates sit within 16 percent of each other, and the reason is bandwidth, in section 10.\n\n| Benchmark | llama.cpp HIP (Q4_K_M, 5.10 bpw) | halogen-server 0.1.4 (.hgn, 6.32 bpw) | vLLM AWQ-INT4, AMD (4.25 bpw) | vLLM, Spark reference (NVFP4, 4-bit) | \n| pp512 | 382.49 ± 0.58 | 668.51 ± 0.64 | 365.40 ± 0.60 | 1978.52 ± 13.13 | \n| pp1024 | 407.60 ± 0.61 | 683.53 ± 9.00 | 310.30 ± 0.20 | 2017.32 ± 17.89 | \n| pp2048 | 417.11 ± 0.65 | 670.18 ± 1.29 | 254.50 ± 2.50 | 2383.97 ± 9.64 | \n| pp4096 | 412.05 ± 0.44 | 662.73 ± 1.82 | 197.90 ± 0.20 | 2346.93 ± 10.17 | \n| pp8192 | 403.27 ± 0.20 | 645.90 ± 0.74 | 145.70 ± 0.40 | 2363.43 ± 13.38 | \n| pp16384 | 383.53 ± 0.10 | 610.42 ± 0.41 | 148.40 ± 0.40 | 2294.55 ± 11.85 | \n| pp32768 | 346.60; n=1 | 550.08 ± 0.54 | 122.14; n=1 | 2089.52 ± 5.76 | \n| tg512 | 12.20 ± 0.00 | 10.49 ± 0.00 | 11.83 ± 0.00 | 12.38 ± 0.01 | \n| tg1024 | 12.19 ± 0.00 | 10.63 ± 0.08; short, 376 actual | 11.39 ± 0.00 | 12.31 ± 0.15 | \n| tg2048 | 12.16 ± 0.00 | 10.71 ± 0.03; short, 578 actual | 10.65 ± 0.01 | 12.61 ± 0.01 | \n| tg4096 | 12.12 ± 0.00 | 10.61 ± 0.13; short, 852 actual | — | 12.54 ± 0.02 | \n\n *Notes:* Cold cache, greedy sampling, means in tokens per second with the stdev across repeats where more than one repeat was made. The three AMD arms run at different precisions, so read the ratios as approximate; The halogen decode points from tg1024 up stopped short of their requested completion length and are labelled with the depth they reached.\n\nThe same three engines produce 10.5, 12.2, and 11.8 tokens per second – a spread of 16 percent, with llama.cpp narrowly ahead. Decode is bound by how fast bytes move; prefill is bound by how much arithmetic can be issued. Engine quality buys you a great deal on the compute-bound path and almost nothing on the memory-bound one.\n\nRemember what I said in the video about `mtp` though: llama.cpp’s MTP head is silently dropped. Build 11870 does not wire qwen35.nextn_predict_layers, so it ignores the 15 blk.64.* tensors in the GGUF, 227.9 MiB or 1.37 percent of the file. There is no speculation in these numbers in other words. I think that makes the llama.cpp decode rate a fair comparison to halogen in serial mode, (i.e. not a fair comparison to mtp or dflash2, which is the same restriction the AMD Qwen ladder in section 4 carries.) So don’t think you’re going to get 10t/s “real world” when you have some options for performance improvement like mtp or dflash2. I just want to compare boxes as fairly as possible.\n\n# \n\nJust to give you an idea of the perf you *can* get with a model that needs lots of compute (like Qwen 27b Dense – which needs more compute per token than qwen 3.8 flash next!!)\n\n..yes.. that’s looking better. Still the same w4a4/fp8r/i4l mixed 33.40 GiB .hgn\n\n# \n\nThis is a bigger model, so worse right? Nope.\n\nFlash-Next runs on both boxes, and on that model the AMD machine measured roughly 2x faster at the corresponding requested depths: 2,002 against 1,023 tokens per second at a nominal 8192, and 2,031 against 941 at a nominal 32768. (The Spark’s actual prompt lengths overshot those labels, 8,896 and 35,709 tokens; the AMD ladder ran exact. Rates are per actual token on both sides, so the comparison is fair per token, but it is not a matched-depth experiment.) So the AMD box is not uniformly slower at prefill. It is slower on the one model and faster on the other.\n\n(**UPDATE:** I learned later that there is a pending patch for Spark for llama.cpp for this exact issue, but that patch doesn’t make it faster than Gorgon Halo – it makes it the same speed. That JUST came to my attention right before I dropped this review so I need to revisit that soon).\n\nThe 27B engine is not slow. It is doing far more work per token: comparing throughput across two architectures requires dividing by the work each token represents, which means counting active parameters rather than stored ones. Flash-Next stores 176.9 billion parameters but computes with 6.7 billion of them per token whereas the 27B computes with all 25.6 billion for every token. That’s what *dense* means. It’s a 3.84x difference in arithmetic per token and that explains most of the gap between these two models on this one box.\n\n### \n\n| **Prompt tokens** | **AMD (t/s)** | **Spark (t/s)** | **AMD / Spark** | \n| **512** | 1423.11 | 693.37 +/- 4.0 | 2.05x | \n| **1024** | 1659.86 | 826.21 +/- 8.2 | 2.01x | \n| **2048** | 1810.46 | 952.78 +/- 5.0 | 1.90x | \n| **4096** | 1902.09 | 1014.29 +/- 4.1 | 1.88x | \n| **8192** | 2002.20 | 1023.34 +/- 11.5 | 1.96x | \n| **16384** | 2032.15 | 1003.00 +/- 5.9 | 2.03x | \n| **32768** | 2031.18 n=1 | 941.10 +/- 13.2 | 2.16x | \n\n \n# \n\nThe GLM segment is not a like-for-like speed comparison and it should not be read as one. The AMD box runs a 3.84 bits-per-weight GGUF with the routed experts resident in GTT. The Spark runs a ~2-bit expert build under a third-party engine. The Spark’s artifact is roughly half the AMD one’s density. Any decode advantage the Spark shows here is substantially a quantization advantage, and any fidelity advantage the AMD box shows is the thing that density bought.\n\n| Quantity | Value | \n| Parameters | 321.3 B | \n| 4-bit floor at 321.3 B | 160.65 GB | \n| AMD pool, default | 92.21 GiB | \n| AMD pool, configured | 176.00 GiB | \n| Spark pool | 121.69 GiB | \n| AMD artifact on disk | 143.54 GiB, 3.84 bits per weight | \n| Spark artifact on disk | 89.84 GiB, experts at about 2 bits | \n| Spark deficit vs the 4-bit floor | 27.93 GiB minimum, before any KV cache | \n| Spark deficit, NVFP4 experts-only artifact | 69.34 GiB | \n\n Prefill pp\n\n| **Requested** | **Actual prompt** | **Overshoot** | **AMD prefill (t/s)** | **Spark prefill (t/s)** | \n| **512** | 512 | +0.0% | 232.78 | 316.94 | \n| **1024** | 1073 | +4.8% | 206.28 | 472.43 | \n| **2048** | 2190 | +6.9% | 280.17 | 612.22 | \n| **4096** | 4422 | +8.0% | 269.64 | 696.29 | \n| **8192** | 8892 | +8.5% | 237.81 | 731.03 | \n| **16384** | 17828 | +8.8% | 197.31 | 745.06 | \n| **32768** | 35701 | +9.0% | 140.86 | 736.80 | \n| checkpoint-assisted |  |  |  |  | \n\n \nAh, but decode performance is pretty spot-on:\n\nThe model fidelity and tests like our Breakout: Clone tests was **much higher** on gorgon halo; that was nice to see. A model this large was better served with more ram.\n\n# \n\nThe AMD box prefills at 651 tokens per second and the Spark at 576. The machine that looks catastrophically slower if you divide tokens by total time is, in steady state, slightly faster. The uncached read was much slower on the AMD box just because it was a different engine setup.\n\nYou can get yourself into a paradoxical situation if you aren’t careful testing here: ds4 sizes its expert cache from available RAM, so the AMD box allocates 133.5 gigabytes against the Spark’s smaller allocation, and then has to fill it – on a from-disk read path. More memory buys a larger cache, which costs a longer cold start… and some weights can be left on disk vs come from ram. For a model this size, on this engine, extra RAM is a cold-start liability in that scenario…\n\n| Parameter | AMD Gorgon Halo (ROCm) | DGX Spark (CUDA) | Ratio | \n| Marginal rate R | 651 t/s | 576 t/s | 1.13x AMD faster | \n| Points in the fit | 3 (pp512, 2048, 8192) | 4 (pp512, 2048, 8192, 32768) | — | \n| Largest residual | 0.87 s | 7.45 s | — | \n| Mean absolute residual | 0.58 s | 4.09 s | — | \n\n \nThe error bars here on prompt processing speed are large enough that “13%” win for AMD here is close to margin of error; the slight advantage to AMD may be down to somewhat better measured apparent memory utilization on the AMD side.\n\n# \n\nWhat about for “Agentic Workloads”  ?  Let’s look at single core first:\n\nHalf the ARM cores really don’t do all that great with branchy code, whereas Gorgon Halo has 16 powerful x86 cores that can run 32 threads.\n\nOne worker, pinned to one physical core. Mean of 3 measured reps after one discarded warm-up.\n\n| Metric | Unit | AMD Zen 5 (cpu4) | Spark Cortex-X925 (cpu19) | Spark Cortex-A725 (cpu4) | AMD / X925 | \n| cpukit int, ALU chain | Mops/s | 872.6 ± 0.21 | 969.0 ± 0.14 | 930.5 ± 0.22 | 0.900 | \n| cpukit vm, branchy scalar | Mops/s | 368.9 ± 2.36 | 715.8 ± 2.56 | 303.8 ± 0.30 | 0.515 | \n| cpukit lat, pointer chase (lower is better) | ns/load | 157.8 ± 0.25 | 116.7 ± 0.20 | 152.9 ± 0.11 | 1.352 | \n| cpukit mem, int64 triad | GB/s | 33.21 ± 0.06 | 47.11 ± 0.08 | 41.88 ± 0.28 | 0.705 | \n| 7-Zip b | MIPS | 8,608.7 ± 164.3 | 8,661.7 ± 8.08 | 4,691.7 ± 8.14 | 0.994 | \n| OpenSSL aes-128-gcm | kbytes/s | 26.75 M ± 42 k | 8.21 M ± 2 k | 2.92 M ± 0.73 k | 3.259 | \n| OpenSSL aes-256-gcm | kbytes/s | 23.55 M ± 247 k | 8.11 M ± 48 k | 2.59 M ± 0.62 k | 2.902 | \n| OpenSSL sha256 | kbytes/s | 2.55 M ± 2 k | 2.45 M ± 3 k | 2.09 M ± 0.25 k | 1.039 | \n| OpenSSL sha512 | kbytes/s | 1.48 M ± 5 k | 1.51 M ± 0.32 k | 1.08 M ± 0.03 k | 0.976 | \n| OpenSSL chacha20-poly1305 | kbytes/s | 6.41 M ± 2 k | 2.15 M ± 0.52 k | 825 k ± 0.03 k | 2.985 | \n| zstd -b1 | MB/s | 2,061.5 ± 2.69 | 751.6 ± 0.81 | 404.7 ± 0.14 | 2.743 | \n| bzip2 -1 | MB/s | 26.80 ± 0.07 | 24.56 ± 0.06 | 15.01 ± 0.01 | 1.091 | \n\n This also reveals some benchmaxxing aspects from Nvidia’s marketing material I hadn’t quite understood until I got to dig in for this review:\n\nBoth cores run the chain at very nearly the same absolute rate – 1306.9 against 1296.4 million operations per second, a 0.8 percent spread – despite the Spark running 1.35x slower on the clock. What? Dividing by gigahertz hands the Spark a 50 percent lead, and turns out that really does belong to the instruction set, not to the core. Which is faster: it depends on whether your compiler fuses, and a benchmark that reports only the ratio is misleading. This has, I think, shown up in Nvidia’s marketing material and I knew it was wrong based on my experience but I couldn’t explain why without thinking about it a bit more and it clicking (I forgot about the fused op from the compiler in other words…). Not every scenario fuses, either to get it done in 25% less clocks (3 clock ticks vs 4).\n\n## \n\nThe all-core figures run the same twelve measurements as the single-core block, with N single-threaded workers instead of one. Single-core and all-core are the same measurement s, just at different worker counts…\n\n| Metric | Unit | AMD 16C/16T | AMD 16C/32T | Spark 20C/20T | AMD SMT gain | \n| cpukit int, ALU chain | Mops/s | 13,583 ± 37.17 | 26,880 ± 117.4 | 18,975 ± 17.48 | 1.979 | \n| cpukit vm, branchy scalar | Mops/s | 5,538.8 ± 38.70 | 8,966.8 ± 39.24 | 11,733 ± 48.15 | 1.619 | \n| cpukit mem, int64 triad | GB/s | 115.0 ± 0.06 | 112.3 ± 0.21 | 181.2 ± 1.10 | 0.977 | \n| 7-Zip b | MIPS | 73,410 ± 86.08 | 117,544 ± 36.30 | 105,329 ± 95.38 | 1.601 | \n| OpenSSL aes-128-gcm | kbytes/s | 355.32 M ± 921 k | 369.31 M ± 2.20 M | 110.92 M ± 608 k | 1.039 | \n| OpenSSL aes-256-gcm | kbytes/s | 314.98 M ± 420 k | 345.60 M ± 232 k | 105.91 M ± 262 k | 1.097 | \n| OpenSSL sha256 | kbytes/s | 39.10 M ± 36 k | 57.79 M ± 99 k | 45.50 M ± 28 k | 1.478 | \n| OpenSSL sha512 | kbytes/s | 21.38 M ± 13 k | 24.40 M ± 33 k | 26.00 M ± 14 k | 1.142 | \n| OpenSSL chacha20-poly1305 | kbytes/s | 93.79 M ± 69 k | 141.60 M ± 48 k | 29.78 M ± 25 k | 1.510 | \n| zstd -b1 | MB/s | 27,389 ± 87.64 | 30,001 ± 155.2 | 11,451 ± 19.22 | 1.095 | \n| bzip2 -1 | MB/s | 382.8 ± 0.36 | 532.5 ± 3.33 | 423.5 ± 0.16 | 1.391 | \n\n Remember Spark’s arm setup is ten Cortex-X925 performance cores and ten Cortex-A725 efficiency cores, so that’s why I’ve got two Spark CPUs in these comparisons.\n\n| Metric | Unit | Cortex-X925 (cpu19) | Cortex-A725 (cpu4) | X925 / A725 | \n| cpukit int, ALU chain | Mops/s | 969.0 | 930.5 | 1.041 | \n| cpukit vm, branchy scalar | Mops/s | 715.8 | 303.8 | 2.356 | \n| cpukit lat, pointer chase | ns/load | 116.7 | 152.9 | 0.763 | \n| cpukit mem, int64 triad | GB/s | 47.11 | 41.88 | 1.125 | \n| 7-Zip b | MIPS | 8,661.7 | 4,691.7 | 1.846 | \n| OpenSSL aes-128-gcm | kbytes/s | 8.21 M | 2.92 M | 2.809 | \n| OpenSSL aes-256-gcm | kbytes/s | 8.11 M | 2.59 M | 3.127 | \n| OpenSSL sha256 | kbytes/s | 2.45 M | 2.09 M | 1.176 | \n| OpenSSL sha512 | kbytes/s | 1.51 M | 1.08 M | 1.400 | \n| OpenSSL chacha20-poly1305 | kbytes/s | 2.15 M | 825 k | 2.604 | \n| zstd -b1 | MB/s | 751.6 | 404.7 | 1.857 | \n| bzip2 -1 | MB/s | 24.56 | 15.01 | 1.637 | \n\n ## \n\n| Metric | Unit | 16C/16T | 16C/32T | Gain | \n| cpukit int, ALU chain | Mops/s | 13,583 | 26,880 | 1.979 | \n| cpukit vm, branchy scalar | Mops/s | 5,538.8 | 8,966.8 | 1.619 | \n| cpukit mem, int64 triad | GB/s | 115.0 | 112.3 | 0.977 | \n| 7-Zip b | MIPS | 73,410 | 117,544 | 1.601 | \n| OpenSSL aes-128-gcm | kbytes/s | 355.32 M | 369.31 M | 1.039 | \n| OpenSSL aes-256-gcm | kbytes/s | 314.98 M | 345.60 M | 1.097 | \n| OpenSSL sha256 | kbytes/s | 39.10 M | 57.79 M | 1.478 | \n| OpenSSL sha512 | kbytes/s | 21.38 M | 24.40 M | 1.142 | \n| OpenSSL chacha20-poly1305 | kbytes/s | 93.79 M | 141.60 M | 1.510 | \n| zstd -b1 | MB/s | 27,389 | 30,001 | 1.095 | \n| bzip2 -1 | MB/s | 382.8 | 532.5 | 1.391 | \n\n A second thread per core buys 1.98x on the integer chain, because that chain is latency-bound and a second thread fills the stalls. It negatively impacts triad (0.977x or ~3% loss) because the memory controller is already saturated at 16 threads and the extra threads only add queueing. SMT helps exactly where there is idle execution to fill, and not when the bottleneck is off-core.\n\nWith this context, the all core table is really something between the two platforms. It depends what you’re doing with your agents! Spark would be a clear winner if all 20 cores could be expected to perform the same, but that isn’t the case.", "url": "https://wpnews.pro/news/gorgon-halo-arrives-in-gmktek-do-you-need-192gb-of-lpddr5", "canonical_source": "https://forum.level1techs.com/t/gorgon-halo-arrives-in-gmktek-do-you-need-192gb-of-lpddr5/259791#post_5", "published_at": "2026-10-31 20:15:09+00:00", "updated_at": "2026-10-31 20:20:07.731380+00:00", "lang": "en", "topics": ["ai-infrastructure", "ai-chips", "large-language-models", "ai-tools"], "entities": ["GMKtec", "Gorgon Halo", "AMD", "Nvidia", "vLLM", "llama.cpp", "halogen-server", "Amazon"], "also_reported_by": [], "alternates": {"html": "https://wpnews.pro/news/gorgon-halo-arrives-in-gmktek-do-you-need-192gb-of-lpddr5", "markdown": "https://wpnews.pro/news/gorgon-halo-arrives-in-gmktek-do-you-need-192gb-of-lpddr5.md", "text": "https://wpnews.pro/news/gorgon-halo-arrives-in-gmktek-do-you-need-192gb-of-lpddr5.txt", "jsonld": "https://wpnews.pro/news/gorgon-halo-arrives-in-gmktek-do-you-need-192gb-of-lpddr5.jsonld"}}