Seymour Cray designed the CDC 6600 (1964), then founded Cray Research, whose Cray-1 (1976) was the first commercially successful vector supercomputer (p. 396). Its designers tied its speed to its size: "a cylindrical shape was chosen for the CRAY-1 in order to keep wiring distances small", and smallness "allows a 12.5 nanosecond clock period" (Russell, 1978). The padded bench around the base, which earned it the name "the world's most expensive love-seat", hid the power supplies and some of the Freon plumbing.
Why Cray threw away the cache: Flynn, SIMD and the vector idea
After this lesson you will place any machine in Flynn's taxonomy by counting its streams, show with numbers why a pipelined vector unit beats an array of processing elements, give the reason behind each design choice of a Cray-style vector machine, and say where 572 of the 578 instructions of scalar DAXPY disappear on VMIPS.
In January 1968 IBM announced the System/360 Model 85, the first commercially available computer with a cache memory. Eight years later Seymour Cray's company shipped the Cray-1. It was "10 times faster than competing machines" and the fastest computer in the world from 1976 to 1982, in the Computer History Museum's words — and it had no data cache at all. Its operands travelled between a main memory of sixteen banks and its registers, among them eight vector registers of 64 elements each.
Lessons 22–28 showed why a modern core starves without its caches. So why would the fastest machine of its decade leave the data cache out, and how could it still win?
A second number points to the answer. On VMIPS, the textbook machine built on the Cray-1's model, the loop Y[i] = a*X[i] + Y[i] over 64 elements takes 6 instructions. The scalar MIPS loop needs 578.
Past the walls of ILP: data-level parallelism
Lesson 8 ended at the limits of ILP, which the notes group as three walls (p. 387): control (a misprediction costs more the deeper the pipeline), memory (misses and pointer chasing starve the out-of-order window) and complexity/energy (renaming, reservation stations and reorder buffers grow faster than the IPC they buy: "a lot of energy is spent to squeeze out a few more IPCs"). The way past is another kind of parallelism: threads (TLP, lesson 29), independent requests (RLP), or data — this lesson and the next two.
Take the plainest loop there is, Z[i] = X[i] + Y[i] for i = 0 … 63. Iteration 17 never needs the result of iteration 16, so in principle all 64 additions could happen at the same moment. Change one index and the picture flips: in X[i] = X[i] + X[i-1], statement S1 of the July 2024 quiz on loop-carried dependences, every addition waits for the one before.
Z[i] = X[i] + Y[i]: data-level parallelism
X[i] = X[i] + X[i−1]: a loop-carried chain
Data-level parallelism (DLP) — the same operation applied independently to many data items, so that no element waits for the result of another: "same instruction, multiple data" (p. 387). It is a property of the program; SIMD and vector hardware are ways of exploiting it.
Why bother, when an out-of-order core would also find those 64 independent additions? Because of what finding them costs. A superscalar core fetches, decodes, renames, schedules and commits every single instruction, and that machinery, not the adder, is where most of its energy goes. A SIMD or vector machine "only needs to fetch one instruction per data operation" (p. 387): one instruction says "add these 64 pairs". Hence the claim this lesson has to justify: on such loops an in-order vector processor can match or beat a complex out-of-order core, at lower energy.
DLP is the same operation on many independent elements; a SIMD or vector machine pays for one instruction and gets many element operations, so the front-end cost per element almost vanishes.
Flynn counts streams, not width
Two machines each start four operations in the same clock cycle. The first is a 4-wide superscalar: it reads four instructions from one program counter — a load, a multiply, an add, an index update — and sends each to its own unit. The second is a SIMD array: it reads one instruction, ADD R1, R2, R3, and broadcasts it to four processing elements, each adding its own pair of registers. Both are parallel. Only one of them is SIMD.
4-wide superscalar: SISD
SIMD array of 4 PEs: SIMD
In 1966 Michael Flynn classified computers by how many instruction streams and how many data streams they handle at once (p. 388):
| one data stream | many data streams | |
|---|---|---|
| one instruction stream | SISD — a scalar RISC pipeline, an in-order MIPS, and also an out-of-order superscalar: one PC, one stream | SIMD — vector processors (Cray, VMIPS), packed-SIMD extensions (MMX, SSE, AVX), GPUs in their warp execution |
| many instruction streams | MISD — essentially hypothetical; fault-tolerant redundant pipelines are sometimes cited | MIMD — multicores, clusters, distributed-memory systems: one PC per thread |
The rule that settles the confusing cases is the notes' own: "Flynn's classification is about streams, not width" (p. 388). A superscalar may issue four, six or eight instructions per cycle, but all come from one PC, each a different instruction on its own operands: parallelism across instructions, ILP, still SISD. A SIMD machine fetches one instruction and applies it to many elements, as ADDVV.D V3, V1, V2 computes V3[i] = V1[i] + V2[i] for every i: parallelism across data, DLP. Multithreaded and multicore processors run one stream per thread: MIMD, TLP. Vector processors are the textbook SIMD machine.
The SIMD machine: one PC, many processing elements
A SIMD machine has a single control unit with one program counter: each instruction is fetched once and broadcast to all the processing elements (PEs), which execute it in lockstep, each on its own local data (p. 390). The notes' picture is a classroom: one teacher says "add 5 to your number", and 32 students do it at once, each in their own notebook. A PE is much simpler than a core — a few registers, an ALU or FPU, sometimes a slice of local memory — and has no PC, no branch predictor and no cache: it relies on the controller.
One PC buys three things (p. 391): energy, with one fetch and decode per operation instead of one per PE; compact code, written once for all PEs; and simplicity, because PEs stepping in lockstep never need to synchronise. The price is lockstep: all PEs execute the same instruction, or some are masked off (lesson 31). A MIMD multicore makes the opposite trade: every core has its own PC and can run anything, and synchronisation — locks, barriers — becomes the programmer's problem.
Real machines mix the two (p. 391): a scalar unit runs ordinary SISD code and the SIMD instructions go to the PE array — MIPS plus the vector unit of VMIPS, scalar x86 plus AVX-512. GPUs, with their thousands of threads, are "essentially SIMD under the hood": a warp of threads executes one instruction at a time in lockstep. The notes' Figure 30 (p. 392) draws a vector processor next to a GPU's SIMD processor, which Hennessy and Patterson call a multithreaded SIMD processor; lesson 32 takes the pair apart.
Count instruction streams and data streams, never instructions per cycle: superscalar = SISD (ILP), vector unit and GPU warp = SIMD (DLP), multicore = MIMD (TLP).
Space or time: arrays of PEs and pipelined vector units
"Not all SIMD is created equal" (p. 394). The first way to build it is the SIMD array — Illiac IV, the Connection Machine: the programmer sees an array of PEs with local memories, and each broadcast instruction runs on all of them at once. Such arrays are awkward to program (you think in PEs, local memories and communication) and handle branches badly: they are "of historical interest". The second way is the vector processor of Cray and VMIPS: the programmer sees vector registers, writes one instruction for a whole array, and the hardware streams the elements through deeply pipelined functional units — "classical SIMD, just presented in a more programmer-friendly way" (p. 392).
The difference shows in time. Suppose the add takes 6 cycles. In the array each PE executes the ADD "exactly like a tiny CPU would" and stays "frozen" until it finishes, so "latency is exposed": every operation pays all of it (p. 395). In the vector unit the add is a pipeline: in cycle 1 the first pair of elements enters the adder, in cycle 2 the second pair enters while the first is still inside, and so on. After the 6-cycle start-up one result leaves every cycle: 64 elements take 6 + 64 = 70 cycles, on a "conveyor belt" where "latency is only paid once".
In space: 4 PEs, each frozen for 6 cycles
In time: 1 adder, 6 elements in flight
Count both machines with the rule of the Tomasulo tables: a result is written \(L\) cycles after its operation starts (\(L\) the latency of the adder, \(n\) the number of elements).
Pipelined unit. Element \(k\) enters the adder in cycle \(k\) and is written \(L\) cycles later (WRITE RESULT = START EXEC + latency):
\[ t_{\text{write}}(k) = k + L \]The last element, \(k = n\), is written in cycle \(n + L\):
\[ T_{\text{vector}} = L + n \]With \(L = 6\) and \(n = 64\): 70 cycles, the notes' count.
Array of \(N\) unpipelined PEs. \(N\) elements start together and keep their PEs frozen for \(L\) cycles; the next \(N\) start \(L\) cycles later. Round \(r\) starts and writes in
\[ t_{\text{start}}(r) = (r-1)L + 1 \] \[ t_{\text{write}}(r) = rL + 1 \]\(n\) elements need \(\lceil n/N \rceil\) rounds, so the last results are written in cycle
\[ T_{\text{array}} = L \left\lceil \frac{n}{N} \right\rceil + 1 \]With \(L = 6\), \(n = 64\) and \(N = 8\): 6 · 8 + 1 = 49 cycles. With \(N = 1\), a single unpipelined adder: 385. The final 1 is the write cycle that the pipeline's \(L + n\) already contains.
Divide the results by the hardware: the pipelined adder alone delivers 64/70 = 0.91 results per cycle, each of the 8 array adders 64/(8 · 49) = 0.16, about one every \(L\) cycles:
\[ \frac{n}{L+n} \quad \text{vs} \quad \frac{1}{L} \]The pipeline wins on hardware, not on latency: one \(L\)-stage pipelined unit does the work of about \(L\) unpipelined ones, once the vector is long enough to keep it full.
Why can a vector unit be pipelined so deeply? Because of element independence: the element entering the adder never needs the result of an element still inside it, since V3[17] = V1[17] + V2[17] does not read V3[16]. No hazard check is needed between consecutive elements, so the unit can be cut into many short stages and clocked fast (p. 397).
The widget adds a third machine: a scalar loop doing the same additions, the body of the papers' strip-mining quiz, Y[i] = X[i] + Y[i]:
LOOP: LD F2, 0(R1) ; X[i]
LD F4, 0(R2) ; Y[i]
FADD F4, F4, F2 ; X[i] + Y[i]
SD F4, 0(R2) ; Y[i] ← F4
ADDUI R1, R1, 8
ADDUI R2, R2, 8
BNE R1, R3, LOOP ; R3 = end of X
Counted optimistically — one cycle for each of the six other instructions, \(L\) cycles for the FADD because the SD waits for its result, no other stall — every element costs \(L + 6\) cycles. The scalar loop also loads and stores each element, which a single ADDVV.D does not: the fair whole-loop comparison is lesson 31's. Watch how often each machine pays the latency.
"A vector unit does its 64 additions at once." It does one per cycle per unit: six or so are in flight at any moment, each at a different stage. Doing 64 at once takes 64 adders; vector machines add parallel copies of a unit as lanes — their PEs — without changing a single instruction (lesson 31).
An array of \(N\) PEs pays the latency once per round of \(N\) elements; a pipelined vector unit pays it once per vector and then streams one result per cycle: one \(L\)-stage pipelined adder does the work of about \(L\) unpipelined ones — on long vectors.
Cray's choices: where the transistors went
When people say "vector processor" they usually mean this Cray-style design, and VMIPS is a simplified version of it (p. 396). Its philosophy, in the notes' words: "don't waste transistors on speculation or caches; spend them on wide datapaths and memory bandwidth" (p. 398). The target is scientific code with long arrays — matrix operations, PDE solvers, simulations — and with no giant instruction window and no speculative logic the result is "much higher throughput per watt than OoO ILP" (p. 398). Five choices follow, each with a reason and a price:
| Choice | Why it fits DLP | What it costs |
|---|---|---|
| 1. One instruction, many elements — the vector ISA | One fetch and decode for 64 element operations; no loop overhead, no loop branches; dependences checked once per vector, not per element | Helps only loops with independent iterations; scalar code runs at scalar speed |
| 2. Register-to-register — vector registers | Each element is loaded once and reused by several instructions; the pipelines stream from registers, one element per cycle in order, instead of stalling on memory, unlike the memory-to-memory vector machines before the Cray-1 (CDC STAR-100) | A large register file with many ports (VMIPS: 4 KB, 16 read and 8 write ports) |
| 3. Deeply pipelined functional units | Element independence allows deep pipelines with no hazard checks between elements: one result per cycle, start-up amortised over the vector | Every instruction pays a start-up latency; short vectors waste most of it |
| 4. Interleaved (banked) main memory | Consecutive words sit in consecutive banks, so one word per cycle streams in although each bank is busy for several cycles (Cray-1: 16 banks, 4 clock periods per access) | Many banks; strides that keep hitting the same bank collide (lesson 31) |
| 5. Little or no data cache | A vector load states exactly which words it needs, and a stream uses each of them once: a cache would add latency and area for no reuse, while the banks give the bandwidth directly | Scalar and irregular code get no cache help; at most a scalar cache serves the scalar side, which the vector side bypasses (p. 397) |
Three supporting pieces complete the machine (p. 397), all put to work in lesson 31: vector mask registers, which switch off elements so that loops with an if stay vectorisable; multiple lanes, parallel copies of the units (4 lanes, 4 elements per cycle); and a scalar unit for control flow and scalar data.
A Cray-style machine bets on regularity: one instruction for many elements, vector registers, deep pipelines, interleaved banks — and no data cache, because a stream has nothing to reuse.
VMIPS, and DAXPY in six instructions
VMIPS is not a commercial computer but Hennessy and Patterson's teaching model: the MIPS you know plus "a Cray-style vector coprocessor", simple enough to count cycles by hand, faithful enough that the counts mean something, and a bridge to the SIMD units of today's processors (p. 399). The February 2025 paper prints its block diagram (notes p. 578), redrawn here.
Its three pillars, plus the scalar side (pp. 399–401):
- Vector register file. Eight registers, each holding 64 elements of 64 bits: 4 KB in all. Its 16 read and 8 write ports, connected to the units by a crossbar, let several units and the load/store unit use it in the same cycle. It is a compiler-controlled buffer between memory and the units: the compiler decides what is loaded and when, so it is not a cache.
- Vector functional units. Five of them — FP add/subtract, FP multiply, FP divide, integer, logical — all fully pipelined, each accepting a new element every cycle. One unit's output can feed another element by element, without waiting for the whole vector: chaining, the vector form of forwarding (lesson 31).
- Vector load/store unit. Moves a whole vector between memory and a register: the memory latency is paid once, then one word per cycle. Memory is interleaved — word 0 in bank 0, word 1 in bank 1 — so a sequential load never waits for a busy bank. Besides unit stride it can load every k-th word (strided access, for matrix columns) and gather or scatter elements through an index vector (sparse data).
- Scalar side. The MIPS core runs the code that does not vectorise, computes addresses and supplies scalar operands such as a.
The instructions, in the papers' spelling (Hennessy and Patterson write LV and SV for L.V and S.V):
| Instruction | What it does |
|---|---|
L.V V1, R1 · S.V V1, R1 | load / store the whole vector V1 at the address in R1 (unit stride) |
LVWS V1, (R1, R2) · SVWS (R1, R2), V1 | load / store with stride R2: every R2-th word |
LVI V1, (R1+V2) · SVI (R1+V2), V1 | gather / scatter: element i at address R1 + V2[i] |
ADDVV.D V1, V2, V3 · ADDVS.D V1, V2, F0 | V1[i] = V2[i] + V3[i] · V1[i] = V2[i] + F0 (vector-vector, vector-scalar) |
SUBVV.D SUBVS.D SUBSV.D · MULVV.D MULVS.D · DIVVV.D DIVVS.D DIVSV.D | the same for subtract, multiply (vector-vector also written MULV.D) and divide; SV puts the scalar first |
SNEVS.D V1, F0 and the other compares (EQ, GT, LT, GE, LE; VV or VS) | compare element by element and set the vector mask register |
MTC1 VLR, R1 · MFC1 R1, VLR | write / read the vector-length register (lesson 31) |
The exam's machines are variations on VMIPS: "32 vectors of 16 elements" in July 2024 and June 2026, of 8 elements in June 2025. Always read the vector length from the question.
DAXPY, instruction by instruction
DAXPY, "Double-precision A·X Plus Y", is the loop of the opening puzzle (p. 402):
\[ Y[i] = a \cdot X[i] + Y[i] \]A BLAS kernel and the inner loop of the Linpack benchmark that ranks supercomputers, it does one multiply and one add per element, with no dependence between elements, so it isolates the effect of vectorisation. The scalar MIPS loop for 64 elements, in the papers' mnemonics:
LD F0, 0(R3) ; F0 ← a
ADDUI R4, R1, 512 ; R4 = end of X
LOOP: LD F2, 0(R1) ; X[i]
FMUL F2, F2, F0 ; a * X[i]
LD F4, 0(R2) ; Y[i]
FADD F4, F4, F2 ; a * X[i] + Y[i]
SD F4, 0(R2) ; Y[i] ← F4
ADDUI R1, R1, 8 ; next X
ADDUI R2, R2, 8 ; next Y
SUB R5, R4, R1 ; elements left?
BNE R5, R0, LOOP ; R0 is always 0
And on VMIPS, the same work:
LD F0, 0(R3) ; F0 ← a
L.V V1, R1 ; V1 ← X[0..63]
MULVS.D V2, V1, F0 ; V2 ← a * X
L.V V3, R2 ; V3 ← Y[0..63]
ADDVV.D V4, V2, V3 ; V4 ← a * X + Y
S.V V4, R2 ; Y ← V4
Set-up, executed once:
LD F0(the scalar a) andADDUI R4(the end of X), 2 instructions.Loop body, executed once per element: 9 instructions. Five do the work — two loads, the multiply, the add, the store — and four only run the loop: two pointer updates, the bound test and the branch.
For 64 elements:
\[ 2 + 9 \times 64 = 578 \]dynamic instructions, the notes' "≈ 578".
VMIPS: the scalar
\[ 578 - 6 = 572 \]LD F0plus one vector instruction per operation of the body; no loop, so no pointers, no bound, no branch:Where the 572 went: the 320 element instructions (5 × 64) became 5 vector instructions, 315 fewer; the 3 × 64 = 192 pointer updates and bound tests vanished, and so did the 64 branches and the bound set-up:
\[ 315 + 192 + 64 + 1 = 572 \]
Fetch and decode are not all: the scalar pipeline also resolves the four dependences that carry the data through the body — LD to FMUL, FMUL to FADD, LD to FADD, FADD to SD — once per element, 256 times; VMIPS resolves each of them once. The widget counts both.
How long the six instructions take is the subject of lesson 31.
The opening puzzle, solved
Back to 1976. A cache pays off when data are reused or when the hardware has to guess what comes next, and a vector loop offers neither: a vector load states exactly which 64 words it wants, and DAXPY uses each once. A stream needs bandwidth and a way to pay latency once, and that is where the Cray-1's transistors went: sixteen banks, each busy for 4 clock periods, delivering one word per clock period (Russell, 1978); pipelined units that pay their latency once per 64 elements; and 4 KB of vector registers, the buffer a cache would have been, filled by the compiler, so nothing misses. The 578 against 6 is the same decision seen from the instruction side.
VMIPS is MIPS plus 8 vector registers of 64 × 64-bit elements (16 read, 8 write ports), five pipelined units and one pipelined load/store unit over interleaved banks; on it, DAXPY's 578 scalar instructions become 6.
Exam-style questions
The February 2025 paper asked an open question on the VMIPS figure of section 5: present its main concepts, then the advantages of vector over scalar execution, each with the feature that provides it. Its model answer is in lesson 31, once convoys and chaining are on the table.
Explain the main concepts and benefits of each one of the following topics of SIMD and vector architectures: 1. Data-level parallelism; 2. Flynn's taxonomy and the class of a superscalar processor; 3. SIMD execution with a single program counter; 4. Array processors vs pipelined vector processors; 5. Vector register file; 6. Deeply pipelined vector functional units; 7. Interleaved memory banks; 8. Little or no data cache.
Show model answer
1. Data-level parallelism. The same operation applied independently to many data items, as in Z[i] = X[i] + Y[i]: no element waits for another. It is a property of the program, exploited by SIMD and vector hardware with one instruction per data operation instead of one per element; the fetch, decode and issue cost per element is divided by the vector length, so it costs far less energy than extracting the same parallelism as ILP.
2. Flynn's taxonomy and the superscalar. Flynn classifies machines by the number of instruction streams and data streams. A superscalar fetches several different instructions per cycle from one program counter: one instruction stream, each instruction on its own operands, so it is SISD and exploits ILP. The benefit of the classification is to separate ILP (more instructions per cycle from one stream), DLP (one instruction on many data, SIMD) and TLP (many streams, MIMD): Flynn counts streams, not width.
3. SIMD with a single PC. One control unit fetches each instruction once and broadcasts it to many processing elements, which execute it in lockstep on their own data. Benefits: one fetch and decode per operation instead of per PE (energy), compact code, no synchronisation between PEs. Drawback: divergent control flow must be handled by masking off elements.
4. Array vs vector processors. An array processor has N processing elements working side by side; an operation with latency L keeps them frozen, so it takes L × ⌈n/N⌉ cycles and the latency is exposed on every round, and the programmer thinks in PEs and local memories. A vector processor pipelines its units: the latency is paid once and then one result per cycle, L + n cycles (6 + 64 = 70), and the programmer thinks in vector registers. On long vectors one L-stage pipelined unit does the work of about L unpipelined ones.
5. Vector register file. Registers holding whole vectors (VMIPS: 8 registers of 64 × 64-bit elements, 16 read and 8 write ports through a crossbar), used register-to-register: each element is loaded once and reused by several instructions, and the pipelines are fed from registers without stalling on memory. It is compiler-controlled, unlike a cache: no tags, no misses.
6. Deeply pipelined functional units. Each unit accepts a new element every cycle. Element independence means no hazard checks between elements, so the pipelines can be deep and fast, and the start-up latency is amortised over the whole vector: about one result per cycle per unit. Cost: every instruction pays its start-up, so short vectors are inefficient.
7. Interleaved memory banks. Consecutive words are placed in consecutive banks; each bank is busy for several cycles after an access, but together they deliver one word per cycle to the vector load/store unit (Cray-1: 16 banks, 4-cycle bank busy time). Benefit: the bandwidth needed by streaming loads and stores; cost: many banks, and conflicts when a stride keeps hitting the same bank.
8. Little or no data cache. Vector accesses are predictable — the instruction states which words it needs — and streaming kernels use each element once, so a cache would add latency and area for little reuse. Bandwidth comes from the banks, latency is amortised by pipelining and buffered in the vector registers; a small scalar cache may serve the scalar side, which the vector side bypasses.
The 22 June 2026 paper asks its 8-point question in exactly this form, there on Tomasulo-style techniques, with five lines per item. For each item write the mechanism in one sentence, then the benefit, then a cost or a condition. Items 2 and 4 carry the two traps of the topic: "superscalar = SIMD" and the notes' "latency × vector length" for arrays.
Let's consider Flynn's taxonomy. In which class is an out-of-order superscalar processor that issues up to 4 instructions per clock cycle from a single thread? (Single answer.)
Show model answer
Answer 1: SISD. Flynn's classification counts instruction and data streams, not issue width: a superscalar fetches all its instructions from one program counter.
The notes file it under "Practical clarification" (p. 388) because it is the classic confusion. A good motivation line: "streams, not width; superscalar = ILP within one stream".
True or false: in a vector processor with fully pipelined functional units, the latency of a functional unit is paid once for each element of the vector.
Show model answer
False. The latency is paid once per vector instruction (the start-up); then the pipeline delivers one result per clock cycle, so n elements take about L + n cycles, not L × n.
The True/False form of the June 2025 paper's GPU quiz, on the idea behind every vector timing in lesson 31. If asked to motivate, give both counts with numbers.
Which features allow a classic (Cray-style) vector processor to keep its functional units busy with little or no data cache? (Multiple answers.)
Show model answer
Answers 1, 2 and 3. Vector accesses are predictable and stream each element once: interleaved banks supply the bandwidth, pipelined units pay the latency once per vector, and the vector registers act as a compiler-managed buffer.
The last option is the trap: caches live on reuse, and the reason vector machines drop them is that streams have none. Choosing it means confusing locality with data-level parallelism — the slip of the notes on p. 387.
Let's consider a vector processor whose FP add unit is fully pipelined with a start-up latency of 6 clock cycles. How many clock cycles does ADDVV.D V3, V1, V2 take on vectors of 64 elements, counting the start-up and then one result per cycle?
Show model answer
For comparison: one unpipelined adder would need 6 × 64 = 384 cycles of computation; an array of 64 unpipelined PEs about 6, with 64 adders instead of one.
The papers' convoy quizzes ignore the start-up (cycles = convoys × vector length, lesson 31); a question about one instruction with a given start-up counts it. Read which of the two the question wants.
Let's consider DAXPY on 64 elements. The scalar MIPS code has 2 set-up instructions and a loop body of 9 instructions executed once per element; the VMIPS code has 6 instructions. By what factor does vectorisation reduce the number of executed instructions?
Show model answer
Write the instruction count before dividing: 9 × 64 = 576 forgets the set-up. If the question asks where the difference goes, 572 = 315 element instructions + 192 pointer and bound updates + 64 branches + 1 set-up.
Check yourself
Which of these are SIMD in Flynn's sense? Select all that apply.
Ask two questions: how many PCs, and does one instruction touch one element or many?
An array of 64 unpipelined PEs with a 6-cycle add finishes a 64-element add in 7 cycles; a single 6-stage pipelined adder needs 70. Why did vector machines choose the pipeline?
Why can a vector add unit be cut into many short pipeline stages without the hazard-detection logic of a scalar pipeline?
VMIPS keeps 4 KB of vector registers next to its functional units. What makes them different from a 4 KB data cache?
An out-of-order superscalar and a vector processor both perform DAXPY's 64 multiplications and 64 additions, with floating-point units of similar cost. Where does the vector machine save most of its energy?
Why does the VMIPS vector register file have 16 read ports and 8 write ports?
Key take-aways
- ILP hit three walls — control, memory, complexity/energy; data-level parallelism, the same operation on many independent elements, lets a machine pay one fetch and decode per data operation instead of one per element.
- Flynn counts instruction and data streams, not instructions per cycle: a superscalar is SISD (ILP), a vector unit or a GPU warp is SIMD (DLP), a multicore is MIMD (TLP).
- An array of \(N\) unpipelined PEs pays the latency on every round, \(L \cdot \lceil n/N \rceil\) cycles; a pipelined vector unit pays it once and then streams one result per cycle, \(L + n\) — so on long vectors one \(L\)-stage pipelined unit does the work of about \(L\) unpipelined ones.
- A Cray-style machine spends its transistors on one instruction for many elements, vector registers, deep pipelines made safe by element independence and interleaved banks for bandwidth — and keeps little or no data cache, because a stream has nothing to reuse.
- VMIPS is MIPS plus 8 vector registers of 64 × 64-bit elements (16 read and 8 write ports), five pipelined functional units and one pipelined load/store unit over interleaved banks.
- DAXPY on 64 elements takes 578 MIPS instructions (2 + 9 × 64) and 6 VMIPS ones; the 572 saved are 315 element instructions, 192 pointer and bound updates, 64 branches and one set-up instruction.
What to watch and read
-
Digital Design and Comp. Arch. — Lecture 19: SIMD Architectures (Vector and Array Processors)
Onur Mutlu, ETH Zürich
Array processors against vector processors — the same operation on many elements in space or in time — drawn step by step: the picture of section 3 before you meet it.
-
The Cray-1 Supercomputer
Computer History Museum
Photos of the machine of the opening puzzle: over 60 miles of hand-laid wire with no segment longer than 3 feet, Freon cooling and 115 kW of power.
-
Vector Computers (6.823, lecture 22)
Joel Emer, with notes by Krste Asanović and Arvind — MIT OpenCourseWare
The Cray-1 block diagram and the vector programming model, in the order of this lesson and the next: compare the diagram with Fig. 4 while you read section 5.
-
The CRAY-1 Computer System
Richard M. Russell, Communications of the ACM, 1978
Tables I and II hold the numbers of this lesson: 16 banks with a 4-clock bank cycle, eight 64-element vector registers, the 6-clock floating-point adder — and chaining in its designers' words, the start of lesson 31.
-
Some Computer Organizations and Their Effectiveness
Michael J. Flynn, IEEE Transactions on Computers, 1972
The four classes in their author's words, with the SIMD machines of the time as examples.