| name | jump-trading-fpga-hft |
| description | Build trading systems in the style of Jump Trading, the high-frequency trading firm pioneering FPGA-based trading. Emphasizes hardware acceleration, network optimization, and nanosecond-level execution. Use when building FPGA trading systems, network-optimized infrastructure, or ultra-low-latency order execution. |
| tags | fpga, hft, low-latency, trading, hardware, networking, market-making, colocation, systems, real-time |
Jump Trading Style Guide
Overview
Jump Trading is a proprietary trading firm known for pushing the boundaries of trading technology. They pioneered FPGA-based trading, invested in microwave networks for faster-than-fiber connectivity, and operate at the absolute frontier of latency optimization.
Core Philosophy
"The speed of light is the only limit we accept."
"Software is too slow. Put it in hardware."
"Network latency is just physics. Compute latency is engineering failure."
Jump believes that when software is too slow, you put the logic in hardware. FPGAs can process market data and generate orders in hundreds of nanoseconds—faster than a CPU can even wake up.
Design Principles
-
Hardware > Software: When latency matters, use FPGAs.
-
Network is Critical: Microwave beats fiber. Co-location beats remote.
-
Picoseconds Matter: At the frontier, every nanosecond is fought for.
-
Deterministic Wins: Jitter is the enemy of consistent performance.
-
Full Stack Ownership: Own everything from NIC to exchange.
When Building Ultra-Low-Latency Systems
Always
- Measure wire-to-wire latency, not component latency
- Use FPGAs for time-critical decisions
- Optimize network path (co-location, cross-connects, switches)
- Process data in the NIC when possible (smart NICs)
- Eliminate all unnecessary hops
- Use hardware timestamps for accurate measurement
Never
- Trust software timestamps
- Use general-purpose switches in the critical path
- Assume network latency is fixed
- Ignore the physical layer (cables, optics, switches)
- Process sequentially when you can pipeline
- Wait for full message when you can cut-through
Prefer
- FPGAs over CPUs for fixed logic
- Cut-through switching over store-and-forward
- Microwave/millimeter-wave over fiber for long distances
- Dedicated lines over shared infrastructure
- Hardware timestamping over software
- Parallel processing over sequential
Code Patterns
FPGA Market Data Parser (Pseudo-Verilog)
// FPGA-based market data parsing and order generation
// Processes UDP multicast market data, generates orders in ~200ns
module market_data_parser (
input wire clk_312_5mhz, // 312.5 MHz clock (3.2ns period)
input wire [63:0] eth_data, // 64-bit data from MAC
input wire eth_valid,
input wire eth_sof, // Start of frame
input wire eth_eof, // End of frame
output reg [63:0] order_data,
output reg order_valid,
output reg [15:0] symbol_id,
output reg [31:0] bid_price,
output reg [31:0] ask_price,
output reg [31:0] bid_size,
output reg [31:0] ask_size
);
// Pipeline stages for parallel processing
reg [2:0] state;
localparam IDLE = 0, PARSE_HEADER = 1, PARSE_SYMBOL = 2,
PARSE_BID = 3, PARSE_ASK = 4, GENERATE_ORDER = 5;
// Pre-computed strategy parameters (loaded at startup)
reg [31:0] fair_value [0:4095]; // Per-symbol fair value
reg [31:0] edge_threshold [0:4095]; // Min edge to trade
reg [31:0] max_position [0:4095]; // Position limits
// Current positions (updated by fill handler)
reg [31:0] positions [0:4095];
always @(posedge clk_312_5mhz) begin
case (state)
IDLE: begin
order_valid <= 0;
if (eth_valid && eth_sof) begin
state <= PARSE_HEADER;
end
end
PARSE_HEADER: begin
// Parse UDP header, extract message type
// Skip IP/UDP headers (known fixed offsets)
if (is_quote_message(eth_data)) begin
state <= PARSE_SYMBOL;
end else begin
state <= IDLE;
end
end
PARSE_SYMBOL: begin
symbol_id <= eth_data[15:0];
state <= PARSE_BID;
end
PARSE_BID: begin
bid_price <= eth_data[31:0];
bid_size <= eth_data[63:32];
state <= PARSE_ASK;
end
PARSE_ASK: begin
ask_price <= eth_data[31:0];
ask_size <= eth_data[63:32];
state <= GENERATE_ORDER;
end
GENERATE_ORDER: begin
// All logic executes in single clock cycle
wire [31:0] fv = fair_value[symbol_id];
wire [31:0] edge = edge_threshold[symbol_id];
wire [31:0] pos = positions[symbol_id];
wire [31:0] max_pos = max_position[symbol_id];
// Buy if bid is below fair value minus edge
wire should_buy = (bid_price < fv - edge) && (pos < max_pos);
// Sell if ask is above fair value plus edge
wire should_sell = (ask_price > fv + edge) && (pos > -max_pos);
if (should_buy) begin
order_data <= build_buy_order(symbol_id, bid_price, bid_size);
order_valid <= 1;
end else if (should_sell) begin
order_data <= build_sell_order(symbol_id, ask_price, ask_size);
order_valid <= 1;
end
state <= IDLE;
end
endcase
end
endmodule
Network Topology Optimization
class NetworkOptimizer:
"""
Jump's network optimization: every nanosecond counts.
Model and optimize the full network path.
"""
def __init__(self):
self.topology = {}
self.latency_measurements = {}
def model_path_latency(self,
source: str,
destination: str) -> LatencyBreakdown:
"""
Break down latency into components.
"""
path = self.find_path(source, destination)
breakdown = LatencyBreakdown()
for i, (node_a, node_b) in enumerate(zip(path[:-1], path[1:])):
link = self.topology[(node_a, node_b)]
prop_delay = link.distance_meters * link.propagation_factor
breakdown.propagation_ns += prop_delay
serial_delay = (link.frame_size_bytes * 8) / link.bandwidth_gbps
breakdown.serialization_ns += serial_delay
if link.device_type == 'cut_through_switch':
breakdown.switching_ns += 300
elif link.device_type == 'store_forward_switch':
breakdown.switching_ns +=
i == :
breakdown.nic_tx_ns += link.nic_tx_latency_ns
i == (path) - :
breakdown.nic_rx_ns += link.nic_rx_latency_ns
breakdown
() -> :
distance_km = .calculate_distance(point_a, point_b)
c =
fiber_speed = c *
fiber_distance = distance_km *
fiber_latency_ms = (fiber_distance / fiber_speed) *
microwave_speed = c *
microwave_distance = distance_km *
microwave_latency_ms = (microwave_distance / microwave_speed) *
{
: fiber_latency_ms,
: microwave_latency_ms,
: fiber_latency_ms - microwave_latency_ms,
: (fiber_latency_ms - microwave_latency_ms) / fiber_latency_ms *
}
Smart NIC Processing
class SmartNICProcessor {
public:
struct PacketContext {
uint64_t timestamp_hw;
uint8_t* packet_data;
uint16_t length;
};
__attribute__((section(".nic_code")))
Action process_packet(PacketContext* ctx) {
auto* eth = reinterpret_cast<EthernetHeader*>(ctx->packet_data);
if (eth->ethertype != ETHERTYPE_IP) {
return Action::PASS_TO_HOST;
}
auto* ip = reinterpret_cast<IPHeader*>(eth + 1);
auto* udp = reinterpret_cast<UDPHeader*>(ip + 1);
if (!is_market_data_multicast(ip->dst_addr, udp->dst_port)) {
return Action::PASS_TO_HOST;
}
auto* msg = reinterpret_cast<MarketDataMessage*>(udp + 1);
if (!is_in_universe(msg->symbol_id)) {
return Action::DROP;
}
ctx->packet_data = (ctx->packet_data, ctx->timestamp_hw);
Action::PASS_TO_HOST;
}
};
Precision Time Protocol (PTP)
class PTPTimeSync {
public:
void configure_ptp_hardware(int nic_fd) {
struct hwtstamp_config config = {};
config.tx_type = HWTSTAMP_TX_ON;
config.rx_filter = HWTSTAMP_FILTER_ALL;
struct ifreq ifr = {};
ifr.ifr_data = (char*)&config;
ioctl(nic_fd, SIOCSHWTSTAMP, &ifr);
struct ethtool_ts_info info = {};
info.cmd = ETHTOOL_GET_TS_INFO;
ifr.ifr_data = (char*)&info;
ioctl(nic_fd, SIOCETHTOOL, &ifr);
char phc_device[32];
snprintf(phc_device, sizeof(phc_device), "/dev/ptp%d", info.phc_index);
phc_fd_ = open(phc_device, O_RDWR);
}
uint64_t get_hardware_time_ns() {
struct ptp_clock_time ptc;
ioctl(phc_fd_, PTP_CLOCK_GETTIME, &ptc);
return ptc.sec * 1000000000ULL + ptc.nsec;
}
uint64_t {
( cmsghdr* cmsg = (msg);
cmsg;
cmsg = (msg, cmsg)) {
(cmsg->cmsg_level == SOL_SOCKET &&
cmsg->cmsg_type == SCM_TIMESTAMPING) {
* ts =
( scm_timestamping*)(cmsg);
ts->ts[].tv_sec * +
ts->ts[].tv_nsec;
}
}
;
}
:
phc_fd_;
};
Wire-to-Wire Latency Measurement
class WireToWireLatency {
public:
struct Measurement {
uint64_t rx_hw_timestamp;
uint64_t tx_hw_timestamp;
uint64_t wire_to_wire_ns;
uint64_t parse_ns;
uint64_t strategy_ns;
uint64_t order_build_ns;
uint64_t tx_queue_ns;
};
void record_tick_to_trade(
uint64_t market_data_rx_hw_ts,
uint64_t order_tx_hw_ts) {
uint64_t latency_ns = order_tx_hw_ts - market_data_rx_hw_ts;
histogram_.record(latency_ns);
if (latency_ns > target_latency_ns_) {
log_slow_path(latency_ns);
}
}
void print_histogram() {
auto stats = histogram_.get_stats();
printf("Wire-to-wire latency:\n");
printf(" p50: %luns\n", stats.p50);
printf(, stats.p99);
(, stats.p999);
(, stats.max);
}
};
Mental Model
Jump approaches ultra-low-latency by asking:
- What's the physics limit? Speed of light × distance
- Where's the compute? Move it to hardware (FPGA/SmartNIC)
- What's the network path? Optimize every hop
- What's the jitter? Worst case matters more than average
- Can we pipeline? Process in parallel, not sequentially
Signature Jump Moves
- FPGA-based trading logic
- Microwave networks for long-haul
- Smart NIC pre-processing
- Hardware PTP time synchronization
- Cut-through switching
- Wire-to-wire latency measurement
- Nanosecond-level optimization
- Co-location at every major exchange
- Full-stack hardware/software ownership