xref: /third_party/alsa-lib/include/ump_msg.h (revision d5ac70f0)
1/* SPDX-License-Identifier: LGPL-2.1+ */
2/**
3 * \file include/ump_msg.h
4 * \brief API library for ALSA rawmidi/UMP interface
5 *
6 * API library for ALSA rawmidi/UMP interface
7 */
8
9#ifndef __ALSA_UMP_MSG_H
10#define __ALSA_UMP_MSG_H
11
12#include <stdint.h>
13
14#ifdef __cplusplus
15extern "C" {
16#endif
17
18/** general UMP packet header in 32bit word */
19typedef struct _snd_ump_msg_hdr {
20#ifdef SNDRV_BIG_ENDIAN_BITFIELD
21	uint8_t type:4;		/**< UMP packet type */
22	uint8_t group:4;	/**< UMP Group */
23	uint8_t status:4;	/**< Status */
24	uint8_t channel:4;	/**< Channel */
25	uint8_t byte1;		/**< First data byte */
26	uint8_t byte2;		/**< Second data byte */
27#else
28	uint8_t byte2;		/**< Second data byte */
29	uint8_t byte1;		/**< First data byte */
30	uint8_t channel:4;	/**< Channel */
31	uint8_t status:4;	/**< Status */
32	uint8_t group:4;	/**< UMP Group */
33	uint8_t type:4;		/**< UMP packet type */
34#endif
35} __attribute((packed)) snd_ump_msg_hdr_t;
36
37/** MIDI 1.0 Note Off / Note On (32bit) */
38typedef struct _snd_ump_msg_midi1_note {
39#ifdef SNDRV_BIG_ENDIAN_BITFIELD
40	uint8_t type:4;		/**< UMP packet type */
41	uint8_t group:4;	/**< UMP Group */
42	uint8_t status:4;	/**< Status */
43	uint8_t channel:4;	/**< Channel */
44	uint8_t note;		/**< Note (7bit) */
45	uint8_t velocity;	/**< Velocity (7bit) */
46#else
47	uint8_t velocity;	/**< Velocity (7bit) */
48	uint8_t note;		/**< Note (7bit) */
49	uint8_t channel:4;	/**< Channel */
50	uint8_t status:4;	/**< Status */
51	uint8_t group:4;	/**< UMP Group */
52	uint8_t type:4;		/**< UMP packet type */
53#endif
54} __attribute((packed)) snd_ump_msg_midi1_note_t;
55
56/** MIDI 1.0 Poly Pressure (32bit) */
57typedef struct _snd_ump_msg_midi1_paf {
58#ifdef SNDRV_BIG_ENDIAN_BITFIELD
59	uint8_t type:4;		/**< UMP packet type */
60	uint8_t group:4;	/**< UMP Group */
61	uint8_t status:4;	/**< Status */
62	uint8_t channel:4;	/**< Channel */
63	uint8_t note;		/** Note (7bit) */
64	uint8_t data;		/** Pressure (7bit) */
65#else
66	uint8_t data;		/** Pressure (7bit) */
67	uint8_t note;		/** Note (7bit) */
68	uint8_t channel:4;	/**< Channel */
69	uint8_t status:4;	/**< Status */
70	uint8_t group:4;	/**< UMP Group */
71	uint8_t type:4;		/**< UMP packet type */
72#endif
73} __attribute((packed)) snd_ump_msg_midi1_paf_t;
74
75/** MIDI 1.0 Control Change (32bit) */
76typedef struct _snd_ump_msg_midi1_cc {
77#ifdef SNDRV_BIG_ENDIAN_BITFIELD
78	uint8_t type:4;		/**< UMP packet type */
79	uint8_t group:4;	/**< UMP Group */
80	uint8_t status:4;	/**< Status */
81	uint8_t channel:4;	/**< Channel */
82	uint8_t index;		/** Control index (7bit) */
83	uint8_t data;		/** Control data (7bit) */
84#else
85	uint8_t data;		/** Control data (7bit) */
86	uint8_t index;		/** Control index (7bit) */
87	uint8_t channel:4;	/**< Channel */
88	uint8_t status:4;	/**< Status */
89	uint8_t group:4;	/**< UMP Group */
90	uint8_t type:4;		/**< UMP packet type */
91#endif
92} __attribute((packed)) snd_ump_msg_midi1_cc_t;
93
94/** MIDI 1.0 Program Change (32bit) */
95typedef struct _snd_ump_msg_midi1_program {
96#ifdef SNDRV_BIG_ENDIAN_BITFIELD
97	uint8_t type:4;		/**< UMP packet type */
98	uint8_t group:4;	/**< UMP Group */
99	uint8_t status:4;	/**< Status */
100	uint8_t channel:4;	/**< Channel */
101	uint8_t program;	/**< Program number (7bit) */
102	uint8_t reserved;	/**< Unused */
103#else
104	uint8_t reserved;	/**< Unused */
105	uint8_t program;	/**< Program number (7bit) */
106	uint8_t channel:4;	/**< Channel */
107	uint8_t status:4;	/**< Status */
108	uint8_t group:4;	/**< UMP Group */
109	uint8_t type:4;		/**< UMP packet type */
110#endif
111} __attribute((packed)) snd_ump_msg_midi1_program_t;
112
113/** MIDI 1.0 Channel Pressure (32bit) */
114typedef struct _snd_ump_msg_midi1_caf {
115#ifdef SNDRV_BIG_ENDIAN_BITFIELD
116	uint8_t type:4;		/**< UMP packet type */
117	uint8_t group:4;	/**< UMP Group */
118	uint8_t status:4;	/**< Status */
119	uint8_t channel:4;	/**< Channel */
120	uint8_t data;		/**< Pressure (7bit) */
121	uint8_t reserved;	/**< Unused */
122#else
123	uint8_t reserved;	/**< Unused */
124	uint8_t data;		/**< Pressure (7bit) */
125	uint8_t channel:4;	/**< Channel */
126	uint8_t status:4;	/**< Status */
127	uint8_t group:4;	/**< UMP Group */
128	uint8_t type:4;		/**< UMP packet type */
129#endif
130} __attribute((packed)) snd_ump_msg_midi1_caf_t;
131
132/** MIDI 1.0 Pitch Bend (32bit) */
133typedef struct _snd_ump_msg_midi1_pitchbend {
134#ifdef SNDRV_BIG_ENDIAN_BITFIELD
135	uint8_t type:4;		/**< UMP packet type */
136	uint8_t group:4;	/**< UMP Group */
137	uint8_t status:4;	/**< Status */
138	uint8_t channel:4;	/**< Channel */
139	uint8_t data_lsb;	/**< LSB of pitchbend (7bit) */
140	uint8_t data_msb;	/**< MSB of pitchbend (7bit) */
141#else
142	uint8_t data_msb;	/**< MSB of pitchbend (7bit) */
143	uint8_t data_lsb;	/**< LSB of pitchbend (7bit) */
144	uint8_t channel:4;	/**< Channel */
145	uint8_t status:4;	/**< Status */
146	uint8_t group:4;	/**< UMP Group */
147	uint8_t type:4;		/**< UMP packet type */
148#endif
149} __attribute((packed)) snd_ump_msg_midi1_pitchbend_t;
150
151/** System Common and Real Time messages (32bit); no channel field */
152typedef struct snd_ump_msg_system {
153#ifdef SNDRV_BIG_ENDIAN_BITFIELD
154	uint8_t type:4;		/**< UMP packet type */
155	uint8_t group:4;	/**< UMP Group */
156	uint8_t status;		/**< Status */
157	uint8_t parm1;		/**< First parameter */
158	uint8_t parm2;		/**< Second parameter */
159#else
160	uint8_t parm1;		/**< First parameter */
161	uint8_t parm2;		/**< Second parameter */
162	uint8_t status;		/**< Status */
163	uint8_t group:4;	/**< UMP Group */
164	uint8_t type:4;		/**< UMP packet type */
165#endif
166} __attribute((packed)) snd_ump_msg_system_t;
167
168/** MIDI 1.0 UMP CVM (32bit) */
169typedef union _snd_ump_msg_midi1 {
170	snd_ump_msg_midi1_note_t	note_on;
171	snd_ump_msg_midi1_note_t	note_off;
172	snd_ump_msg_midi1_paf_t		poly_pressure;
173	snd_ump_msg_midi1_cc_t		control_change;
174	snd_ump_msg_midi1_program_t	program_change;
175	snd_ump_msg_midi1_caf_t		channel_pressure;
176	snd_ump_msg_midi1_pitchbend_t	pitchbend;
177	snd_ump_msg_system_t		system;
178	snd_ump_msg_hdr_t		hdr;
179	uint32_t			raw;
180} snd_ump_msg_midi1_t;
181
182/** MIDI 2.0 Note-on/off attribute type */
183enum {
184	SND_UMP_MIDI2_NOTE_ATTR_NO_DATA		= 0x00,	/**< No attribute data */
185	SND_UMP_MIDI2_NOTE_ATTR_MANUFACTURER	= 0x01,	/**< Manufacturer specific */
186	SND_UMP_MIDI2_NOTE_ATTR_PROFILE		= 0x02,	/**< Profile specific */
187	SND_UMP_MIDI2_NOTE_ATTR_PITCH79		= 0x03,	/**< Pitch 7.9 */
188};
189
190/* MIDI 2.0 Note Off / Note On (64bit) */
191typedef struct _snd_ump_msg_midi2_note {
192#ifdef SNDRV_BIG_ENDIAN_BITFIELD
193	uint8_t type:4;		/**< UMP packet type */
194	uint8_t group:4;	/**< UMP Group */
195	uint8_t status:4;	/**< Status */
196	uint8_t channel:4;	/**< Channel */
197	uint8_t note;		/**< Note (7bit) */
198	uint8_t attr_type;	/**< Attribute type */
199
200	uint16_t velocity;	/**< Velocity (16bit) */
201	uint16_t attr_data;	/**< Attribute data (16bit) */
202#else
203	uint8_t attr_type;	/**< Attribute type */
204	uint8_t note;		/**< Note (7bit) */
205	uint8_t channel:4;	/**< Channel */
206	uint8_t status:4;	/**< Status */
207	uint8_t group:4;	/**< UMP Group */
208	uint8_t type:4;		/**< UMP packet type */
209
210	uint16_t attr_data;	/**< Attribute data (16bit) */
211	uint16_t velocity;	/**< Velocity (16bit) */
212#endif
213} __attribute((packed)) snd_ump_msg_midi2_note_t;
214
215/** MIDI 2.0 Poly Pressure (64bit) */
216typedef struct _snd_ump_msg_midi2_paf {
217#ifdef SNDRV_BIG_ENDIAN_BITFIELD
218	uint8_t type:4;		/**< UMP packet type */
219	uint8_t group:4;	/**< UMP Group */
220	uint8_t status:4;	/**< Status */
221	uint8_t channel:4;	/**< Channel */
222	uint8_t note;		/**< Note (7bit) */
223	uint8_t reserved;	/**< Unused */
224
225	uint32_t data;		/**< Pressure (32bit) */
226#else
227	uint8_t reserved;	/**< Unused */
228	uint8_t note;		/**< Note (7bit) */
229	uint8_t channel:4;	/**< Channel */
230	uint8_t status:4;	/**< Status */
231	uint8_t group:4;	/**< UMP Group */
232	uint8_t type:4;		/**< UMP packet type */
233
234	uint32_t data;		/**< Pressure (32bit) */
235#endif
236} __attribute((packed)) snd_ump_msg_midi2_paf_t;
237
238/** MIDI 2.0 Per-Note Controller (64bit) */
239typedef struct _snd_ump_msg_midi2_per_note_cc {
240#ifdef SNDRV_BIG_ENDIAN_BITFIELD
241	uint8_t type:4;		/**< UMP packet type */
242	uint8_t group:4;	/**< UMP Group */
243	uint8_t status:4;	/**< Status */
244	uint8_t channel:4;	/**< Channel */
245	uint8_t note;		/**< Note (7bit) */
246	uint8_t index;		/**< Control index (8bit) */
247
248	uint32_t data;		/**< Data (32bit) */
249#else
250	uint8_t index;		/**< Control index (8bit) */
251	uint8_t note;		/**< Note (7bit) */
252	uint8_t channel:4;	/**< Channel */
253	uint8_t status:4;	/**< Status */
254	uint8_t group:4;	/**< UMP Group */
255	uint8_t type:4;		/**< UMP packet type */
256
257	uint32_t data;		/**< Data (32bit) */
258#endif
259} __attribute((packed)) snd_ump_msg_midi2_per_note_cc_t;
260
261/** MIDI 2.0 per-note management flag bits */
262enum {
263	SND_UMP_MIDI2_PNMGMT_RESET_CONTROLLERS	= 0x01,	/**< Reset (set) per-note controllers */
264	SND_UMP_MIDI2_PNMGMT_DETACH_CONTROLLERS	= 0x02,	/**< Detach per-note controllers */
265};
266
267/** MIDI 2.0 Per-Note Management (64bit) */
268typedef struct _snd_ump_msg_midi2_per_note_mgmt {
269#ifdef SNDRV_BIG_ENDIAN_BITFIELD
270	uint8_t type:4;		/**< UMP packet type */
271	uint8_t group:4;	/**< UMP Group */
272	uint8_t status:4;	/**< Status */
273	uint8_t channel:4;	/**< Channel */
274	uint8_t note;		/**< Note (7bit) */
275	uint8_t flags;		/**< Option flags (8bit) */
276
277	uint32_t reserved;	/**< Unused */
278#else
279	uint8_t flags;		/**< Option flags (8bit) */
280	uint8_t note;		/**< Note (7bit) */
281	uint8_t channel:4;	/**< Channel */
282	uint8_t status:4;	/**< Status */
283	uint8_t group:4;	/**< UMP Group */
284	uint8_t type:4;		/**< UMP packet type */
285
286	uint32_t reserved;	/**< Unused */
287#endif
288} __attribute((packed)) snd_ump_msg_midi2_per_note_mgmt_t;
289
290/** MIDI 2.0 Control Change (64bit) */
291typedef struct _snd_ump_msg_midi2_cc {
292#ifdef SNDRV_BIG_ENDIAN_BITFIELD
293	uint8_t type:4;		/**< UMP packet type */
294	uint8_t group:4;	/**< UMP Group */
295	uint8_t status:4;	/**< Status */
296	uint8_t channel:4;	/**< Channel */
297	uint8_t index;		/**< Control index (7bit) */
298	uint8_t reserved;	/**< Unused */
299
300	uint32_t data;		/**< Control data (32bit) */
301#else
302	uint8_t reserved;	/**< Unused */
303	uint8_t index;		/**< Control index (7bit) */
304	uint8_t channel:4;	/**< Channel */
305	uint8_t status:4;	/**< Status */
306	uint8_t group:4;	/**< UMP Group */
307	uint8_t type:4;		/**< UMP packet type */
308
309	uint32_t data;		/**< Control data (32bit) */
310#endif
311} __attribute((packed)) snd_ump_msg_midi2_cc_t;
312
313/** MIDI 2.0 Registered Controller (RPN) / Assignable Controller (NRPN) (64bit) */
314typedef struct _snd_ump_msg_midi2_rpn {
315#ifdef SNDRV_BIG_ENDIAN_BITFIELD
316	uint8_t type:4;		/**< UMP packet type */
317	uint8_t group:4;	/**< UMP Group */
318	uint8_t status:4;	/**< Status */
319	uint8_t channel:4;	/**< Channel */
320	uint8_t bank;		/**< Bank number (7bit) */
321	uint8_t index;		/**< Control index (7bit) */
322
323	uint32_t data;		/**< Data (32bit) */
324#else
325	uint8_t index;		/**< Control index (7bit) */
326	uint8_t bank;		/**< Bank number (7bit) */
327	uint8_t channel:4;	/**< Channel */
328	uint8_t status:4;	/**< Status */
329	uint8_t group:4;	/**< UMP Group */
330	uint8_t type:4;		/**< UMP packet type */
331
332	uint32_t data;		/**< Data (32bit) */
333#endif
334} __attribute((packed)) snd_ump_msg_midi2_rpn_t;
335
336/** MIDI 2.0 Program Change (64bit) */
337typedef struct _snd_ump_msg_midi2_program {
338#ifdef SNDRV_BIG_ENDIAN_BITFIELD
339	uint8_t type:4;		/**< UMP packet type */
340	uint8_t group:4;	/**< UMP Group */
341	uint8_t status:4;	/**< Status */
342	uint8_t channel:4;	/**< Channel */
343	uint16_t reserved:15;	/**< Unused */
344	uint16_t bank_valid:1;	/**< Option flag: bank valid */
345
346	uint8_t program;	/**< Program number (7bit) */
347	uint8_t reserved2;	/**< Unused */
348	uint8_t bank_msb;	/**< MSB of bank (8bit) */
349	uint8_t bank_lsb;	/**< LSB of bank (7bit) */
350#else
351	uint16_t bank_valid:1;	/**< Option flag: bank valid */
352	uint16_t reserved:15;	/**< Unused */
353	uint8_t channel:4;	/**< Channel */
354	uint8_t status:4;	/**< Status */
355	uint8_t group:4;	/**< UMP Group */
356	uint8_t type:4;		/**< UMP packet type */
357
358	uint8_t bank_lsb;	/**< LSB of bank (7bit) */
359	uint8_t bank_msb;	/**< MSB of bank (8bit) */
360	uint8_t reserved2;	/**< Unused */
361	uint8_t program;	/**< Program number (7bit) */
362#endif
363} __attribute((packed)) snd_ump_msg_midi2_program_t;
364
365/** MIDI 2.0 Channel Pressure (64bit) */
366typedef struct _snd_ump_msg_midi2_caf {
367#ifdef SNDRV_BIG_ENDIAN_BITFIELD
368	uint8_t type:4;		/**< UMP packet type */
369	uint8_t group:4;	/**< UMP Group */
370	uint8_t status:4;	/**< Status */
371	uint8_t channel:4;	/**< Channel */
372	uint16_t reserved;	/**< Unused */
373
374	uint32_t data;		/** Data (32bit) */
375#else
376	uint16_t reserved;	/**< Unused */
377	uint8_t channel:4;	/**< Channel */
378	uint8_t status:4;	/**< Status */
379	uint8_t group:4;	/**< UMP Group */
380	uint8_t type:4;		/**< UMP packet type */
381
382	uint32_t data;		/** Data (32bit) */
383#endif
384} __attribute((packed)) snd_ump_msg_midi2_caf_t;
385
386/* MIDI 2.0 Pitch Bend (64bit) */
387typedef struct _snd_ump_msg_midi2_pitchbend {
388#ifdef SNDRV_BIG_ENDIAN_BITFIELD
389	uint8_t type:4;		/**< UMP packet type */
390	uint8_t group:4;	/**< UMP Group */
391	uint8_t status:4;	/**< Status */
392	uint8_t channel:4;	/**< Channel */
393	uint16_t reserved;	/**< Unused */
394
395	uint32_t data;		/** Data (32bit) */
396#else
397	uint16_t reserved;	/**< Unused */
398	uint8_t channel:4;	/**< Channel */
399	uint8_t status:4;	/**< Status */
400	uint8_t group:4;	/**< UMP Group */
401	uint8_t type:4;		/**< UMP packet type */
402
403	uint32_t data;		/** Data (32bit) */
404#endif
405} __attribute((packed)) snd_ump_msg_midi2_pitchbend_t;
406
407/* MIDI 2.0 Per-Note Pitch Bend (64bit) */
408typedef struct _snd_ump_msg_midi2_per_note_pitchbend {
409#ifdef __BIG_ENDIAN_BITFIELD
410	uint8_t type:4;		/**< UMP packet type */
411	uint8_t group:4;	/**< UMP Group */
412	uint8_t status:4;	/**< Status */
413	uint8_t channel:4;	/**< Channel */
414	uint8_t note;		/**< Note (7bit) */
415	uint8_t reserved;	/**< Unused */
416
417	uint32_t data;		/**< Data (32bit) */
418#else
419	/* 0 */
420	uint8_t reserved;	/**< Unused */
421	uint8_t note;		/**< Note (7bit) */
422	uint8_t channel:4;	/**< Channel */
423	uint8_t status:4;	/**< Status */
424	uint8_t group:4;	/**< UMP Group */
425	uint8_t type:4;		/**< UMP packet type */
426
427	uint32_t data;		/**< Data (32bit) */
428#endif
429} __attribute((packed)) snd_ump_msg_midi2_per_note_pitchbend_t;
430
431/** MIDI2 UMP packet (64bit little-endian) */
432typedef union _snd_ump_msg_midi2 {
433	snd_ump_msg_midi2_note_t	note_on;
434	snd_ump_msg_midi2_note_t	note_off;
435	snd_ump_msg_midi2_paf_t		poly_pressure;
436	snd_ump_msg_midi2_per_note_cc_t	per_note_acc;
437	snd_ump_msg_midi2_per_note_cc_t	per_note_rcc;
438	snd_ump_msg_midi2_per_note_mgmt_t per_note_mgmt;
439	snd_ump_msg_midi2_cc_t		control_change;
440	snd_ump_msg_midi2_rpn_t		rpn;
441	snd_ump_msg_midi2_rpn_t		nrpn;
442	snd_ump_msg_midi2_rpn_t		relative_rpn;
443	snd_ump_msg_midi2_rpn_t		relative_nrpn;
444	snd_ump_msg_midi2_program_t	program_change;
445	snd_ump_msg_midi2_caf_t		channel_pressure;
446	snd_ump_msg_midi2_pitchbend_t	pitchbend;
447	snd_ump_msg_midi2_per_note_pitchbend_t per_note_pitchbend;
448	snd_ump_msg_hdr_t		hdr;
449	uint32_t			raw[2];
450} snd_ump_msg_midi2_t;
451
452/**
453 * UMP message type
454 */
455enum {
456	SND_UMP_MSG_TYPE_UTILITY		= 0x00,	/* Utility messages */
457	SND_UMP_MSG_TYPE_SYSTEM			= 0x01,	/* System messages */
458	SND_UMP_MSG_TYPE_MIDI1_CHANNEL_VOICE	= 0x02,	/* MIDI 1.0 messages */
459	SND_UMP_MSG_TYPE_DATA			= 0x03,	/* 7bit SysEx messages */
460	SND_UMP_MSG_TYPE_MIDI2_CHANNEL_VOICE	= 0x04,	/* MIDI 2.0 messages */
461	SND_UMP_MSG_TYPE_EXTENDED_DATA		= 0x05,	/* 8bit data message */
462	SND_UMP_MSG_TYPE_FLEX_DATA		= 0x0d,	/* Flexible data messages */
463	SND_UMP_MSG_TYPE_STREAM			= 0x0f,	/* Stream messages */
464};
465
466/**
467 * UMP MIDI 1.0 / 2.0 message status code (4bit)
468 */
469enum {
470	SND_UMP_MSG_PER_NOTE_RCC	= 0x0,
471	SND_UMP_MSG_PER_NOTE_ACC	= 0x1,
472	SND_UMP_MSG_RPN			= 0x2,
473	SND_UMP_MSG_NRPN		= 0x3,
474	SND_UMP_MSG_RELATIVE_RPN	= 0x4,
475	SND_UMP_MSG_RELATIVE_NRPN	= 0x5,
476	SND_UMP_MSG_PER_NOTE_PITCHBEND	= 0x6,
477	SND_UMP_MSG_NOTE_OFF		= 0x8,
478	SND_UMP_MSG_NOTE_ON		= 0x9,
479	SND_UMP_MSG_POLY_PRESSURE	= 0xa,
480	SND_UMP_MSG_CONTROL_CHANGE	= 0xb,
481	SND_UMP_MSG_PROGRAM_CHANGE	= 0xc,
482	SND_UMP_MSG_CHANNEL_PRESSURE	= 0xd,
483	SND_UMP_MSG_PITCHBEND		= 0xe,
484	SND_UMP_MSG_PER_NOTE_MGMT	= 0xf,
485};
486
487/**
488 * MIDI System / Realtime message status code (8bit)
489 */
490enum {
491	SND_UMP_MSG_REALTIME		= 0xf0, /* mask */
492	SND_UMP_MSG_SYSEX_START		= 0xf0,
493	SND_UMP_MSG_MIDI_TIME_CODE	= 0xf1,
494	SND_UMP_MSG_SONG_POSITION	= 0xf2,
495	SND_UMP_MSG_SONG_SELECT		= 0xf3,
496	SND_UMP_MSG_TUNE_REQUEST	= 0xf6,
497	SND_UMP_MSG_SYSEX_END		= 0xf7,
498	SND_UMP_MSG_TIMING_CLOCK	= 0xf8,
499	SND_UMP_MSG_START		= 0xfa,
500	SND_UMP_MSG_CONTINUE		= 0xfb,
501	SND_UMP_MSG_STOP		= 0xfc,
502	SND_UMP_MSG_ACTIVE_SENSING	= 0xfe,
503	SND_UMP_MSG_RESET		= 0xff,
504};
505
506/** MIDI 2.0 SysEx / Data Status; same values for both 7-bit and 8-bit SysEx */
507enum {
508	SND_UMP_SYSEX_STATUS_SINGLE	= 0,
509	SND_UMP_SYSEX_STATUS_START	= 1,
510	SND_UMP_SYSEX_STATUS_CONTINUE	= 2,
511	SND_UMP_SYSEX_STATUS_END	= 3,
512};
513
514/** UMP Utility Type Status (type 0x0) **/
515enum {
516	SND_UMP_UTILITY_MSG_STATUS_NOOP		= 0x00,
517	SND_UMP_UTILITY_MSG_STATUS_JR_CLOCK	= 0x01,
518	SND_UMP_UTILITY_MSG_STATUS_JR_TSTAMP	= 0x02,
519	SND_UMP_UTILITY_MSG_STATUS_DCTPQ	= 0x03,
520	SND_UMP_UTILITY_MSG_STATUS_DC		= 0x04,
521};
522
523/** UMP Stream Message Status (type 0xf) */
524enum {
525	SND_UMP_STREAM_MSG_STATUS_EP_DISCOVERY	= 0x00,
526	SND_UMP_STREAM_MSG_STATUS_EP_INFO	= 0x01,
527	SND_UMP_STREAM_MSG_STATUS_DEVICE_INFO	= 0x02,
528	SND_UMP_STREAM_MSG_STATUS_EP_NAME	= 0x03,
529	SND_UMP_STREAM_MSG_STATUS_PRODUCT_ID	= 0x04,
530	SND_UMP_STREAM_MSG_STATUS_STREAM_CFG_REQUEST = 0x05,
531	SND_UMP_STREAM_MSG_STATUS_STREAM_CFG	= 0x06,
532	SND_UMP_STREAM_MSG_STATUS_FB_DISCOVERY	= 0x10,
533	SND_UMP_STREAM_MSG_STATUS_FB_INFO	= 0x11,
534	SND_UMP_STREAM_MSG_STATUS_FB_NAME	= 0x12,
535	SND_UMP_STREAM_MSG_STATUS_START_CLIP	= 0x20,
536	SND_UMP_STREAM_MSG_STATUS_END_CLIP	= 0x21,
537};
538
539/** UMP Endpoint Discovery filter bitmap */
540enum {
541	SND_UMP_STREAM_MSG_REQUEST_EP_INFO	= (1U << 0),
542	SND_UMP_STREAM_MSG_REQUEST_DEVICE_INFO	= (1U << 1),
543	SND_UMP_STREAM_MSG_REQUEST_EP_NAME	= (1U << 2),
544	SND_UMP_STREAM_MSG_REQUEST_PRODUCT_ID	= (1U << 3),
545	SND_UMP_STREAM_MSG_REQUEST_STREAM_CFG	= (1U << 4),
546};
547
548/** UMP Function Block Discovery filter bitmap */
549enum {
550	SND_UMP_STREAM_MSG_REQUEST_FB_INFO	= (1U << 0),
551	SND_UMP_STREAM_MSG_REQUEST_FB_NAME	= (1U << 1),
552};
553
554/** UMP Endpoint Info capability bits (used for protocol request/notify, too) */
555enum {
556	SND_UMP_STREAM_MSG_EP_INFO_CAP_TXJR	= (1U << 0), /* Sending JRTS */
557	SND_UMP_STREAM_MSG_EP_INFO_CAP_RXJR	= (1U << 1), /* Receiving JRTS */
558	SND_UMP_STREAM_MSG_EP_INFO_CAP_MIDI1	= (1U << 8), /* MIDI 1.0 */
559	SND_UMP_STREAM_MSG_EP_INFO_CAP_MIDI2	= (1U << 9), /* MIDI 2.0 */
560};
561
562/** UMP Endpoint / Function Block name string format bits */
563enum {
564	SND_UMP_STREAM_MSG_FORMAT_SINGLE	= 0,
565	SND_UMP_STREAM_MSG_FORMAT_START		= 1,
566	SND_UMP_STREAM_MSG_FORMAT_CONTINUE	= 2,
567	SND_UMP_STREAM_MSG_FORMAT_END		= 3,
568};
569
570/**
571 * \brief get UMP status (4bit) from 32bit UMP message header
572 */
573static inline uint8_t snd_ump_msg_hdr_status(uint32_t ump)
574{
575	return (ump >> 20) & 0x0f;
576}
577
578/**
579 * \brief get UMP channel (4bit) from 32bit UMP message header
580 */
581static inline uint8_t snd_ump_msg_hdr_channel(uint32_t ump)
582{
583	return (ump >> 16) & 0x0f;
584}
585
586/**
587 * \brief get UMP message type (4bit) from 32bit UMP message header
588 */
589static inline uint8_t snd_ump_msg_hdr_type(uint32_t ump)
590{
591	return (ump >> 28);
592}
593
594/**
595 * \brief check if the given UMP type is a groupless message
596 */
597static inline int snd_ump_msg_type_is_groupless(uint8_t type)
598{
599	return type == SND_UMP_MSG_TYPE_UTILITY || type == SND_UMP_MSG_TYPE_STREAM;
600}
601
602/**
603 * \brief get UMP group (4bit) from 32bit UMP message header
604 */
605static inline uint8_t snd_ump_msg_hdr_group(uint32_t ump)
606{
607	return (ump >> 24) & 0x0f;
608}
609
610/**
611 * \brief get UMP status from UMP packet pointer
612 */
613static inline uint8_t snd_ump_msg_status(const uint32_t *ump)
614{
615	return snd_ump_msg_hdr_status(*ump);
616}
617
618/**
619 * \brief get UMP channel from UMP packet pointer
620 */
621static inline uint8_t snd_ump_msg_channel(const uint32_t *ump)
622{
623	return snd_ump_msg_hdr_channel(*ump);
624}
625
626/**
627 * \brief get UMP message type from UMP packet pointer
628 */
629static inline uint8_t snd_ump_msg_type(const uint32_t *ump)
630{
631	return snd_ump_msg_hdr_type(*ump);
632}
633
634/**
635 * \brief get UMP group from UMP packet pointer
636 */
637static inline uint8_t snd_ump_msg_group(const uint32_t *ump)
638{
639	return snd_ump_msg_hdr_group(*ump);
640}
641
642/**
643 * \brief get UMP sysex message status
644 */
645static inline uint8_t snd_ump_sysex_msg_status(const uint32_t *ump)
646{
647	return (*ump >> 20) & 0xf;
648}
649
650/**
651 * \brief get UMP sysex message length
652 */
653static inline uint8_t snd_ump_sysex_msg_length(const uint32_t *ump)
654{
655	return (*ump >> 16) & 0xf;
656}
657
658int snd_ump_msg_sysex_expand(const uint32_t *ump, uint8_t *buf, size_t maxlen,
659			     size_t *filled);
660
661#ifdef __cplusplus
662}
663#endif
664
665#endif /* __ALSA_UMP_MSG_H */
666