What is an opcode?
An opcode is a unit of computation with:- Inputs: Arguments that provide data (constants, variables, audio streams)
- Outputs: Results produced by the opcode
- State: Internal data that persists between calls
- Functions: Code that executes at different rates (init, k-rate, a-rate)
Opcode entry structure
Each opcode is defined by anOENTRY structure:
include/csoundCore.h:90
Type strings
FromEngine/entry.c:26, input and output types include:
- Basic types
- Polymorphic
- Special codes
- Arrays
i- i-rate scalar (initialization time)k- k-rate scalar (control rate)a- a-rate vector (audio rate)S- Stringf- Frequency variable (special k-rate)w- Spectral variable (FFT data)
From
Engine/entry.c:73, array types use external format in OENTRY strings (e.g., "k[]") which is converted to internal format (e.g., "[k]") by split_args() at runtime.Opcode registration
Opcodes are registered in tables that Csound reads at startup:Engine/entry.c:78
Opcode database
FromEngine/README.md, the opcode database is managed by entry.c. At initialization:
- Built-in opcodes are registered from
opcodlst_1[] - Plugin opcodes are discovered and loaded
- Hash tables map names to
OENTRYstructures - Overloaded opcodes stored in
OENTRIESarrays
include/csoundCore.h:106
Opcode lifecycle
Compilation phase
When orchestra code is compiled:- Parsing: Orchestra parser identifies opcode calls
- Lookup: Compiler finds matching
OENTRYin database - Type checking: Argument types validated against
intypes/outypes - Code generation:
TEXTstructure created linking toOENTRY
include/csoundCore.h:116
Engine/csound_orc_compile.c:1, compilation orchestrates this process.
Instance creation
When an instrument instance activates:- Memory allocation:
dsblksizbytes allocated for opcode state - Initialization:
initfunction called once - Chain linking: Opcode added to instrument’s
nxtiornxtpchain
Engine/insert.c:26
Execution
During performance:Opcode implementation
Data structure
Every opcode defines a data structure inheriting fromOPDS:
OPDS header provides:
- Links to next opcode in chain
- Pointer to parent instrument instance
- Pointer to opcode’s
TEXTstructure
Init function
The init function runs once when the instance starts:Performance function
The performance function runs every k-period:Opcodes/butter.c:58.
Registration
Register the opcode in the entry table:Opcode categories
Built-in opcodes (OOps/)
FromOOps/README.md, internal opcodes include:
Signal generators
ugens2.c, ugens3.c, ugens4.c, oscils.cOscillators, noise, sample playback, FM synthesis
Signal processors
ugens5.c, ugens6.c, vdelay.cFilters, delays, LPC, reverb
Analysis/resynthesis
fftlib.c, pvsanal.c, pstream.cFFT, phase vocoder, spectral processing
Control/utility
ugens1.c, goto_ops.c, schedule.cEnvelopes, control flow, event scheduling
Plugin opcodes (Opcodes/)
External opcodes in dynamically loaded libraries:- afilters.c: Advanced filters
- biquad.c: Biquad filters
- buchla.c: Buchla-style modules
- cellular.c: Cellular automata
- compress.c: Dynamics processors
- Many more…
User-defined opcodes (UDOs)
Users can define opcodes in Csound language:Engine/README.md, UDOs are handled by udo.c:
Engine/udo.c:1
Engine/udo.c:34:
- Parsed as pseudo-instruments
- Compiled to internal representation
- Registered in opcode database
- Called like built-in opcodes
Polymorphic opcodes
Opcodes can be overloaded with different type signatures:Type polymorphism
The type system (fromEngine/csound_type_system.c) enables:
- Generic types: Opcodes work with multiple types
- Array polymorphism: Same opcode for scalar and array versions
- User-defined types: Opcodes operating on custom structures
Engine/entry.c:96:
.S suffix distinguishes the string version.
Opcode flags
Theflags field in OENTRY controls behavior:
- Thread safety: Can opcode run in parallel?
- State requirements: Pure function or stateful?
- Output characteristics: Signal vs. control
Advanced features
Auxiliary memory (AUXCH)
For dynamic buffers:include/csoundCore.h:194
Engine/README.md, managed by auxfd.c:
File handles (FDCH)
For file I/O:include/csoundCore.h:186
Async operations
For non-blocking operations:include/csoundCore.h:210
Error handling
Opcodes report errors via:include/csound.h:90, error codes:
Performance optimization
Inline small opcodes
Frequently used opcodes benefit from inlining to avoid function call overhead.Cache-friendly data layout
Arrange state variables for sequential access:SIMD processing
Use vector instructions for parallel sample processing where possible.Related topics
Architecture
Overall system design
Audio engine
Audio processing details
Instruments
How opcodes combine into instruments
Plugin development
Creating custom opcodes