• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 %{
2 /*
3  * Copyright © 2018 Intel Corporation
4  *
5  * Permission is hereby granted, free of charge, to any person obtaining a
6  * copy of this software and associated documentation files (the "Software"),
7  * to deal in the Software without restriction, including without limitation
8  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
9  * and/or sell copies of the Software, and to permit persons to whom the
10  * Software is furnished to do so, subject to the following conditions:
11  *
12  * The above copyright notice and this permission notice (including the next
13  * paragraph) shall be included in all copies or substantial portions of the
14  * Software.
15  *
16  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
19  * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
21  * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
22  * IN THE SOFTWARE.
23  */
24 
25 #include <stdio.h>
26 #include <stdlib.h>
27 #include <string.h>
28 #include <strings.h>
29 #include "brw_asm_internal.h"
30 
31 #undef yyerror
32 #ifdef YYBYACC
33 struct YYLTYPE;
34 void yyerror (struct YYLTYPE *, char *);
35 #else
36 void yyerror (char *);
37 #endif
38 
39 #undef ALIGN16
40 
41 #define YYLTYPE YYLTYPE
42 typedef struct YYLTYPE
43 {
44 	int first_line;
45 	int first_column;
46 	int last_line;
47 	int last_column;
48 } YYLTYPE;
49 
50 enum message_level {
51 	WARN,
52 	ERROR,
53 };
54 
55 int yydebug = 1;
56 
57 static void
message(enum message_level level,YYLTYPE * location,const char * fmt,...)58 message(enum message_level level, YYLTYPE *location,
59 	const char *fmt, ...)
60 {
61 	static const char *level_str[] = { "warning", "error" };
62 	va_list args;
63 
64 	if (location)
65 		fprintf(stderr, "%s:%d:%d: %s: ", input_filename,
66 		        location->first_line,
67 		        location->first_column, level_str[level]);
68 	else
69 		fprintf(stderr, "%s:%s: ", input_filename, level_str[level]);
70 
71 	va_start(args, fmt);
72 	vfprintf(stderr, fmt, args);
73 	va_end(args);
74 }
75 
76 #define warn(flag, l, fmt, ...) 				 \
77 	do {							 \
78 		if (warning_flags & WARN_ ## flag)		 \
79 			message(WARN, l, fmt, ## __VA_ARGS__);	 \
80 	} while (0)
81 
82 #define error(l, fmt, ...)				   	 \
83 	do {						   	 \
84 		message(ERROR, l, fmt, ## __VA_ARGS__);	   	 \
85 	} while (0)
86 
87 static bool
isPowerofTwo(unsigned int x)88 isPowerofTwo(unsigned int x)
89 {
90 	return x && (!(x & (x - 1)));
91 }
92 
93 static struct brw_reg
set_direct_src_operand(struct brw_reg * reg,int type)94 set_direct_src_operand(struct brw_reg *reg, int type)
95 {
96 	return brw_make_reg(reg->file,
97                             reg->nr,
98                             reg->subnr,
99                             0,		// negate
100                             0,		// abs
101                             type,
102                             0,		// vstride
103                             0,		// width
104                             0,		// hstride
105                             BRW_SWIZZLE_NOOP,
106                             WRITEMASK_XYZW);
107 }
108 
109 static void
i965_asm_unary_instruction(int opcode,struct brw_codegen * p,struct brw_reg dest,struct brw_reg src0)110 i965_asm_unary_instruction(int opcode, struct brw_codegen *p,
111 		           struct brw_reg dest, struct brw_reg src0)
112 {
113 	switch (opcode) {
114 	case BRW_OPCODE_BFREV:
115 		brw_BFREV(p, dest, src0);
116 		break;
117 	case BRW_OPCODE_CBIT:
118 		brw_CBIT(p, dest, src0);
119 		break;
120 	case BRW_OPCODE_MOV:
121 		brw_MOV(p, dest, src0);
122 		break;
123 	case BRW_OPCODE_FBL:
124 		brw_FBL(p, dest, src0);
125 		break;
126 	case BRW_OPCODE_FRC:
127 		brw_FRC(p, dest, src0);
128 		break;
129 	case BRW_OPCODE_FBH:
130 		brw_FBH(p, dest, src0);
131 		break;
132 	case BRW_OPCODE_NOT:
133 		brw_NOT(p, dest, src0);
134 		break;
135 	case BRW_OPCODE_RNDE:
136 		brw_RNDE(p, dest, src0);
137 		break;
138 	case BRW_OPCODE_RNDZ:
139 		brw_RNDZ(p, dest, src0);
140 		break;
141 	case BRW_OPCODE_RNDD:
142 		brw_RNDD(p, dest, src0);
143 		break;
144 	case BRW_OPCODE_LZD:
145 		brw_LZD(p, dest, src0);
146 		break;
147 	case BRW_OPCODE_RNDU:
148 		fprintf(stderr, "Opcode BRW_OPCODE_RNDU unhandled\n");
149 		break;
150 	default:
151 		fprintf(stderr, "Unsupported unary opcode\n");
152 	}
153 }
154 
155 static void
i965_asm_binary_instruction(int opcode,struct brw_codegen * p,struct brw_reg dest,struct brw_reg src0,struct brw_reg src1)156 i965_asm_binary_instruction(int opcode,
157 			    struct brw_codegen *p,
158 			    struct brw_reg dest,
159 			    struct brw_reg src0,
160 			    struct brw_reg src1)
161 {
162 	switch (opcode) {
163 	case BRW_OPCODE_ADDC:
164 		brw_ADDC(p, dest, src0, src1);
165 		break;
166 	case BRW_OPCODE_BFI1:
167 		brw_BFI1(p, dest, src0, src1);
168 		break;
169 	case BRW_OPCODE_DP2:
170 		brw_DP2(p, dest, src0, src1);
171 		break;
172 	case BRW_OPCODE_DP3:
173 		brw_DP3(p, dest, src0, src1);
174 		break;
175 	case BRW_OPCODE_DP4:
176 		brw_DP4(p, dest, src0, src1);
177 		break;
178 	case BRW_OPCODE_DPH:
179 		brw_DPH(p, dest, src0, src1);
180 		break;
181 	case BRW_OPCODE_LINE:
182 		brw_LINE(p, dest, src0, src1);
183 		break;
184 	case BRW_OPCODE_MAC:
185 		brw_MAC(p, dest, src0, src1);
186 		break;
187 	case BRW_OPCODE_MACH:
188 		brw_MACH(p, dest, src0, src1);
189 		break;
190 	case BRW_OPCODE_PLN:
191 		brw_PLN(p, dest, src0, src1);
192 		break;
193 	case BRW_OPCODE_ROL:
194 		brw_ROL(p, dest, src0, src1);
195 		break;
196 	case BRW_OPCODE_ROR:
197 		brw_ROR(p, dest, src0, src1);
198 		break;
199 	case BRW_OPCODE_SUBB:
200 		brw_SUBB(p, dest, src0, src1);
201 		break;
202 	case BRW_OPCODE_ADD:
203 		brw_ADD(p, dest, src0, src1);
204 		break;
205 	case BRW_OPCODE_CMP:
206 		/* Third parameter is conditional modifier
207 		 * which gets updated later
208 		 */
209 		brw_CMP(p, dest, 0, src0, src1);
210 		break;
211 	case BRW_OPCODE_AND:
212 		brw_AND(p, dest, src0, src1);
213 		break;
214 	case BRW_OPCODE_ASR:
215 		brw_ASR(p, dest, src0, src1);
216 		break;
217 	case BRW_OPCODE_AVG:
218 		brw_AVG(p, dest, src0, src1);
219 		break;
220 	case BRW_OPCODE_OR:
221 		brw_OR(p, dest, src0, src1);
222 		break;
223 	case BRW_OPCODE_SEL:
224 		brw_SEL(p, dest, src0, src1);
225 		break;
226 	case BRW_OPCODE_SHL:
227 		brw_SHL(p, dest, src0, src1);
228 		break;
229 	case BRW_OPCODE_SHR:
230 		brw_SHR(p, dest, src0, src1);
231 		break;
232 	case BRW_OPCODE_XOR:
233 		brw_XOR(p, dest, src0, src1);
234 		break;
235 	case BRW_OPCODE_MUL:
236 		brw_MUL(p, dest, src0, src1);
237 		break;
238 	default:
239 		fprintf(stderr, "Unsupported binary opcode\n");
240 	}
241 }
242 
243 static void
i965_asm_ternary_instruction(int opcode,struct brw_codegen * p,struct brw_reg dest,struct brw_reg src0,struct brw_reg src1,struct brw_reg src2)244 i965_asm_ternary_instruction(int opcode,
245 			     struct brw_codegen *p,
246 			     struct brw_reg dest,
247 			     struct brw_reg src0,
248 			     struct brw_reg src1,
249 			     struct brw_reg src2)
250 {
251 	switch (opcode) {
252 	case BRW_OPCODE_MAD:
253 		brw_MAD(p, dest, src0, src1, src2);
254 		break;
255 	case BRW_OPCODE_CSEL:
256 		brw_CSEL(p, dest, src0, src1, src2);
257 		break;
258 	case BRW_OPCODE_LRP:
259 		brw_LRP(p, dest, src0, src1, src2);
260 		break;
261 	case BRW_OPCODE_BFE:
262 		brw_BFE(p, dest, src0, src1, src2);
263 		break;
264 	case BRW_OPCODE_BFI2:
265 		brw_BFI2(p, dest, src0, src1, src2);
266 		break;
267 	case BRW_OPCODE_DP4A:
268 		brw_DP4A(p, dest, src0, src1, src2);
269 		break;
270 	case BRW_OPCODE_ADD3:
271 		brw_ADD3(p, dest, src0, src1, src2);
272 		break;
273 	default:
274 		fprintf(stderr, "Unsupported ternary opcode\n");
275 	}
276 }
277 
278 static void
i965_asm_set_instruction_options(struct brw_codegen * p,struct options options)279 i965_asm_set_instruction_options(struct brw_codegen *p,
280 				 struct options options)
281 {
282 	brw_eu_inst_set_access_mode(p->devinfo, brw_last_inst,
283 			         options.access_mode);
284 	brw_eu_inst_set_mask_control(p->devinfo, brw_last_inst,
285 				  options.mask_control);
286 	if (p->devinfo->ver < 12) {
287 		brw_eu_inst_set_thread_control(p->devinfo, brw_last_inst,
288 					    options.thread_control);
289 		brw_eu_inst_set_no_dd_check(p->devinfo, brw_last_inst,
290 					 options.no_dd_check);
291 		brw_eu_inst_set_no_dd_clear(p->devinfo, brw_last_inst,
292 					 options.no_dd_clear);
293 	} else {
294 		enum opcode opcode = brw_eu_inst_opcode(p->isa, brw_last_inst);
295 		brw_eu_inst_set_swsb(p->devinfo, brw_last_inst,
296 		                  tgl_swsb_encode(p->devinfo, options.depinfo,
297 						  opcode));
298 	}
299 	brw_eu_inst_set_debug_control(p->devinfo, brw_last_inst,
300 			           options.debug_control);
301 	if (brw_has_branch_ctrl(p->devinfo, brw_eu_inst_opcode(p->isa, brw_last_inst))) {
302 		if (options.acc_wr_control)
303 			error(NULL, "Instruction does not support AccWrEnable\n");
304 
305 		brw_eu_inst_set_branch_control(p->devinfo, brw_last_inst,
306 		                            options.branch_control);
307 	} else if (options.branch_control) {
308 		error(NULL, "Instruction does not support BranchCtrl\n");
309 	} else if (p->devinfo->ver < 20) {
310 		brw_eu_inst_set_acc_wr_control(p->devinfo, brw_last_inst,
311 					    options.acc_wr_control);
312 	}
313 	brw_eu_inst_set_cmpt_control(p->devinfo, brw_last_inst,
314 				  options.compaction);
315 }
316 
317 static void
add_label(struct brw_codegen * p,const char * label_name,enum instr_label_type type)318 add_label(struct brw_codegen *p, const char* label_name, enum instr_label_type type)
319 {
320 	if (!label_name) {
321 		return;
322 	}
323 
324 	struct instr_label *label = rzalloc(p->mem_ctx, struct instr_label);
325 
326 	label->name = ralloc_strdup(p->mem_ctx, label_name);
327 	label->offset = p->next_insn_offset;
328 	label->type = type;
329 
330 	list_addtail(&label->link, &instr_labels);
331 }
332 
333 %}
334 
335 %locations
336 
337 %start ROOT
338 
339 %union {
340 	char *string;
341 	double number;
342 	int integer;
343 	unsigned long long int llint;
344 	struct brw_reg reg;
345 	enum brw_reg_type reg_type;
346 	struct brw_codegen *program;
347 	struct predicate predicate;
348 	struct condition condition;
349 	struct options options;
350 	struct instoption instoption;
351 	struct msgdesc msgdesc;
352 	struct tgl_swsb depinfo;
353 	brw_eu_inst *instruction;
354 }
355 
356 %token ABS
357 %token COLON
358 %token COMMA
359 %token DOT
360 %token LANGLE RANGLE
361 %token LCURLY RCURLY
362 %token LPAREN RPAREN
363 %token LSQUARE RSQUARE
364 %token PLUS MINUS
365 %token SEMICOLON
366 %token ASSIGN
367 
368 /* datatypes */
369 %token <integer> TYPE_B TYPE_UB
370 %token <integer> TYPE_W TYPE_UW
371 %token <integer> TYPE_D TYPE_UD
372 %token <integer> TYPE_Q TYPE_UQ
373 %token <integer> TYPE_V TYPE_UV
374 %token <integer> TYPE_F TYPE_HF
375 %token <integer> TYPE_DF
376 %token <integer> TYPE_VF
377 
378 /* label */
379 %token <string> JUMP_LABEL
380 %token <string> JUMP_LABEL_TARGET
381 
382 /* opcodes */
383 %token <integer> ADD ADD3 ADDC AND ASR AVG
384 %token <integer> BFE BFI1 BFI2 BFB BFREV BRC BRD BREAK
385 %token <integer> CALL CALLA CASE CBIT CMP CMPN CONT CSEL
386 %token <integer> DIM DO DPAS DPASW DP2 DP3 DP4 DP4A DPH
387 %token <integer> ELSE ENDIF FBH FBL FORK FRC
388 %token <integer> GOTO
389 %token <integer> HALT
390 %token <integer> IF ILLEGAL
391 %token <integer> JMPI JOIN
392 %token <integer> LINE LRP LZD
393 %token <integer> MAC MACH MAD MADM MATH MOV MOVI MUL MREST MSAVE
394 %token <integer> NENOP NOP NOT
395 %token <integer> OR
396 %token <integer> PLN POP PUSH
397 %token <integer> RET RNDD RNDE RNDU RNDZ ROL ROR
398 %token <integer> SEL SENDS SENDSC SHL SHR SMOV SUBB SYNC
399 %token <integer> SEND_GFX4 SENDC_GFX4 SEND_GFX12 SENDC_GFX12
400 %token <integer> WAIT WHILE
401 %token <integer> XOR
402 
403 /* extended math functions */
404 %token <integer> COS EXP FDIV INV INVM INTDIV INTDIVMOD INTMOD LOG POW RSQ
405 %token <integer> RSQRTM SIN SINCOS SQRT
406 
407 /* sync instruction */
408 %token <integer> ALLRD ALLWR FENCE BAR HOST
409 %type <integer> sync_function
410 %type <reg> sync_arg
411 
412 /* shared functions for send */
413 %token CONST CRE DATA DP_DATA_1 GATEWAY PIXEL_INTERP RENDER SAMPLER
414 %token THREAD_SPAWNER URB VME DP_SAMPLER RT_ACCEL SLM TGM UGM
415 
416 /* message details for send */
417 %token MSGDESC_BEGIN SRC1_LEN EX_BSO MSGDESC_END
418 %type <msgdesc> msgdesc msgdesc_parts;
419 
420 /* Conditional modifiers */
421 %token <integer> EQUAL GREATER GREATER_EQUAL LESS LESS_EQUAL NOT_EQUAL
422 %token <integer> NOT_ZERO OVERFLOW UNORDERED ZERO
423 
424 /* register Access Modes */
425 %token ALIGN1 ALIGN16
426 
427 /* accumulator write control */
428 %token ACCWREN
429 
430 /* compaction control */
431 %token CMPTCTRL
432 
433 /* mask control (WeCtrl) */
434 %token WECTRL
435 
436 /* debug control */
437 %token BREAKPOINT
438 
439 /* dependency control */
440 %token NODDCLR NODDCHK
441 
442 /* end of thread */
443 %token EOT
444 
445 /* mask control */
446 %token MASK_DISABLE;
447 
448 /* predicate control */
449 %token <integer> ANYV ALLV ANY2H ALL2H ANY4H ALL4H ANY8H ALL8H ANY16H ALL16H
450 %token <integer> ANY32H ALL32H
451 
452 /* round instructions */
453 %token <integer> ROUND_INCREMENT
454 
455 /* staturation */
456 %token SATURATE
457 
458 /* thread control */
459 %token ATOMIC SWITCH
460 
461 /* branch control */
462 %token BRANCH_CTRL
463 
464 /* quater control */
465 %token QTR_2Q QTR_3Q QTR_4Q QTR_2H QTR_2N QTR_3N QTR_4N QTR_5N
466 %token QTR_6N QTR_7N QTR_8N
467 
468 /* channels */
469 %token <integer> X Y Z W
470 
471 /* reg files */
472 %token GENREGFILE
473 
474 /* vertical stride in register region */
475 %token VxH
476 
477 /* register type */
478 %token <integer> GENREG ADDRREG ACCREG FLAGREG NOTIFYREG STATEREG
479 %token <integer> CONTROLREG IPREG PERFORMANCEREG THREADREG CHANNELENABLEREG
480 %token <integer> MASKREG SCALARREG
481 
482 %token <integer> INTEGER
483 %token <llint> LONG
484 %token NULL_TOKEN
485 
486 %nonassoc SUBREGNUM
487 %left PLUS MINUS
488 %nonassoc DOT
489 %nonassoc EMPTYEXECSIZE
490 %nonassoc LPAREN
491 
492 %type <integer> execsize exp
493 %type <llint> exp2
494 
495 /* predicate control */
496 %type <integer> predctrl predstate
497 %type <predicate> predicate
498 
499 /* conditional modifier */
500 %type <condition> cond_mod
501 %type <integer> condModifiers
502 
503 /* instruction options  */
504 %type <options> instoptions instoption_list
505 %type <instoption> instoption
506 
507 /* writemask */
508 %type <integer> writemask_x writemask_y writemask_z writemask_w
509 %type <integer> writemask
510 
511 /* dst operand */
512 %type <reg> dst dstoperand dstoperandex dstoperandex_typed dstreg
513 %type <integer> dstregion
514 
515 %type <integer> saturate
516 %type <reg> relativelocation2
517 
518 /* src operand */
519 %type <reg> directsrcoperand directsrcaccoperand indirectsrcoperand srcacc
520 %type <reg> srcarcoperandex srcaccimm srcarcoperandex_typed srcimm
521 %type <reg> indirectgenreg indirectregion
522 %type <reg> immreg src reg32 payload directgenreg_list addrparam region
523 %type <reg> region_wh directgenreg
524 %type <reg> desc ex_desc reg32a
525 %type <integer> swizzle
526 
527 /* registers */
528 %type <reg> accreg addrreg channelenablereg controlreg flagreg ipreg scalarreg
529 %type <reg> notifyreg nullreg performancereg threadcontrolreg statereg maskreg
530 %type <integer> subregnum
531 
532 /* register types */
533 %type <reg_type> reg_type imm_type
534 
535 /* immediate values */
536 %type <llint> immval
537 
538 /* instruction opcodes */
539 %type <integer> unaryopcodes binaryopcodes binaryaccopcodes ternaryopcodes
540 %type <integer> sendop sendsop
541 %type <instruction> sendopcode sendsopcode
542 
543 %type <integer> negate abs chansel math_function sharedfunction
544 
545 %type <string> jumplabeltarget
546 %type <string> jumplabel
547 
548 /* SWSB */
549 %token <integer> REG_DIST_CURRENT
550 %token <integer> REG_DIST_FLOAT
551 %token <integer> REG_DIST_INT
552 %token <integer> REG_DIST_LONG
553 %token <integer> REG_DIST_ALL
554 %token <integer> REG_DIST_MATH
555 %token <integer> REG_DIST_SCALAR
556 %token <integer> SBID_ALLOC
557 %token <integer> SBID_WAIT_SRC
558 %token <integer> SBID_WAIT_DST
559 
560 %type <depinfo> depinfo
561 
562 %code {
563 
564 static void
add_instruction_option(struct options * options,struct instoption opt)565 add_instruction_option(struct options *options, struct instoption opt)
566 {
567 	if (opt.type == INSTOPTION_DEP_INFO) {
568 		if (opt.depinfo_value.regdist) {
569 			options->depinfo.regdist = opt.depinfo_value.regdist;
570 			options->depinfo.pipe = opt.depinfo_value.pipe;
571 		} else {
572 			options->depinfo.sbid = opt.depinfo_value.sbid;
573 			options->depinfo.mode = opt.depinfo_value.mode;
574 		}
575 		return;
576 	}
577 	if (opt.type == INSTOPTION_CHAN_OFFSET) {
578 		options->chan_offset = opt.uint_value;
579 		return;
580 	}
581 	switch (opt.uint_value) {
582 	case ALIGN1:
583 		options->access_mode = BRW_ALIGN_1;
584 		break;
585 	case ALIGN16:
586 		options->access_mode = BRW_ALIGN_16;
587 		break;
588 	case SWITCH:
589 		options->thread_control |= BRW_THREAD_SWITCH;
590 		break;
591 	case ATOMIC:
592 		options->thread_control |= BRW_THREAD_ATOMIC;
593 		break;
594 	case BRANCH_CTRL:
595 		options->branch_control = true;
596 		break;
597 	case NODDCHK:
598 		options->no_dd_check = true;
599 		break;
600 	case NODDCLR:
601 		options->no_dd_clear = true;
602 		break;
603 	case MASK_DISABLE:
604 		options->mask_control |= BRW_MASK_DISABLE;
605 		break;
606 	case BREAKPOINT:
607 		options->debug_control = BRW_DEBUG_BREAKPOINT;
608 		break;
609 	case WECTRL:
610 		options->mask_control |= BRW_WE_ALL;
611 		break;
612 	case CMPTCTRL:
613 		options->compaction = true;
614 		break;
615 	case ACCWREN:
616 		options->acc_wr_control = true;
617 		break;
618 	case EOT:
619 		options->end_of_thread = true;
620 		break;
621 	}
622 }
623 }
624 %%
625 
626 ROOT:
627 	instrseq
628 	;
629 
630 instrseq:
631 	instrseq instruction SEMICOLON
632 	| instrseq relocatableinstruction SEMICOLON
633 	| instruction SEMICOLON
634 	| relocatableinstruction SEMICOLON
635 	| instrseq jumplabeltarget
636 	| jumplabeltarget
637 	;
638 
639 /* Instruction Group */
640 instruction:
641 	unaryinstruction
642 	| binaryinstruction
643 	| binaryaccinstruction
644 	| mathinstruction
645 	| nopinstruction
646 	| waitinstruction
647 	| ternaryinstruction
648 	| sendinstruction
649 	| illegalinstruction
650 	| syncinstruction
651 	;
652 
653 relocatableinstruction:
654 	jumpinstruction
655 	| branchinstruction
656 	| breakinstruction
657 	| loopinstruction
658 	;
659 
660 illegalinstruction:
661 	ILLEGAL execsize instoptions
662 	{
663 		brw_next_insn(p, $1);
664 		brw_eu_inst_set_exec_size(p->devinfo, brw_last_inst, $2);
665 		i965_asm_set_instruction_options(p, $3);
666 	}
667 	;
668 
669 /* Unary instruction */
670 unaryinstruction:
671 	predicate unaryopcodes saturate cond_mod execsize dst srcaccimm	instoptions
672 	{
673 		brw_set_default_access_mode(p, $8.access_mode);
674 		i965_asm_unary_instruction($2, p, $6, $7);
675 		brw_pop_insn_state(p);
676 		i965_asm_set_instruction_options(p, $8);
677 		brw_eu_inst_set_cond_modifier(p->devinfo, brw_last_inst,
678 					   $4.cond_modifier);
679 
680 		if (!brw_eu_inst_flag_reg_nr(p->devinfo, brw_last_inst)) {
681 			brw_eu_inst_set_flag_reg_nr(p->devinfo,
682 						 brw_last_inst,
683 						 $4.flag_reg_nr);
684 			brw_eu_inst_set_flag_subreg_nr(p->devinfo,
685 						    brw_last_inst,
686 						    $4.flag_subreg_nr);
687 		}
688 
689 		if ($7.file != IMM) {
690 			brw_eu_inst_set_src0_vstride(p->devinfo, brw_last_inst,
691 						  $7.vstride);
692 		}
693 		brw_eu_inst_set_saturate(p->devinfo, brw_last_inst, $3);
694 		brw_eu_inst_set_exec_size(p->devinfo, brw_last_inst, $5);
695 		brw_eu_inst_set_group(p->devinfo, brw_last_inst, $8.chan_offset);
696 	}
697 	;
698 
699 unaryopcodes:
700 	BFREV
701 	| CBIT
702 	| DIM
703 	| FBH
704 	| FBL
705 	| FRC
706 	| LZD
707 	| MOV
708 	| NOT
709 	| RNDD
710 	| RNDE
711 	| RNDU
712 	| RNDZ
713 	;
714 
715 /* Binary instruction */
716 binaryinstruction:
717 	predicate binaryopcodes saturate cond_mod execsize dst srcimm srcimm instoptions
718 	{
719 		brw_set_default_access_mode(p, $9.access_mode);
720 		i965_asm_binary_instruction($2, p, $6, $7, $8);
721 		i965_asm_set_instruction_options(p, $9);
722 		brw_eu_inst_set_cond_modifier(p->devinfo, brw_last_inst,
723 					   $4.cond_modifier);
724 
725 		if (!brw_eu_inst_flag_reg_nr(p->devinfo, brw_last_inst)) {
726 			brw_eu_inst_set_flag_reg_nr(p->devinfo, brw_last_inst,
727 					         $4.flag_reg_nr);
728 			brw_eu_inst_set_flag_subreg_nr(p->devinfo, brw_last_inst,
729 						    $4.flag_subreg_nr);
730 		}
731 
732 		brw_eu_inst_set_saturate(p->devinfo, brw_last_inst, $3);
733 		brw_eu_inst_set_exec_size(p->devinfo, brw_last_inst, $5);
734 		brw_eu_inst_set_group(p->devinfo, brw_last_inst, $9.chan_offset);
735 
736 		brw_pop_insn_state(p);
737 	}
738 	;
739 
740 binaryopcodes:
741 	ADDC
742 	| BFI1
743 	| DP2
744 	| DP3
745 	| DP4
746 	| DPH
747 	| LINE
748 	| MAC
749 	| MACH
750 	| MUL
751 	| PLN
752 	| ROL
753 	| ROR
754 	| SUBB
755 	;
756 
757 /* Binary acc instruction */
758 binaryaccinstruction:
759 	predicate binaryaccopcodes saturate cond_mod execsize dst srcacc srcimm instoptions
760 	{
761 		brw_set_default_access_mode(p, $9.access_mode);
762 		i965_asm_binary_instruction($2, p, $6, $7, $8);
763 		brw_pop_insn_state(p);
764 		i965_asm_set_instruction_options(p, $9);
765 		brw_eu_inst_set_cond_modifier(p->devinfo, brw_last_inst,
766 					   $4.cond_modifier);
767 
768 		if (!brw_eu_inst_flag_reg_nr(p->devinfo, brw_last_inst)) {
769 			brw_eu_inst_set_flag_reg_nr(p->devinfo,
770 						 brw_last_inst,
771 						 $4.flag_reg_nr);
772 			brw_eu_inst_set_flag_subreg_nr(p->devinfo,
773 						    brw_last_inst,
774 						    $4.flag_subreg_nr);
775 		}
776 
777 		brw_eu_inst_set_saturate(p->devinfo, brw_last_inst, $3);
778 		brw_eu_inst_set_exec_size(p->devinfo, brw_last_inst, $5);
779 		brw_eu_inst_set_group(p->devinfo, brw_last_inst, $9.chan_offset);
780 	}
781 	;
782 
783 binaryaccopcodes:
784 	ADD
785 	| AND
786 	| ASR
787 	| AVG
788 	| CMP
789 	| CMPN
790 	| OR
791 	| SEL
792 	| SHL
793 	| SHR
794 	| XOR
795 	;
796 
797 /* Math instruction */
798 mathinstruction:
799 	predicate MATH saturate math_function execsize dst src srcimm instoptions
800 	{
801 		brw_set_default_access_mode(p, $9.access_mode);
802 		gfx6_math(p, $6, $4, $7, $8);
803 		i965_asm_set_instruction_options(p, $9);
804 		brw_eu_inst_set_exec_size(p->devinfo, brw_last_inst, $5);
805 		brw_eu_inst_set_saturate(p->devinfo, brw_last_inst, $3);
806 		brw_eu_inst_set_group(p->devinfo, brw_last_inst, $9.chan_offset);
807 		brw_pop_insn_state(p);
808 	}
809 	;
810 
811 math_function:
812 	COS
813 	| EXP
814 	| FDIV
815 	| INV
816 	| INVM
817 	| INTDIV
818 	| INTDIVMOD
819 	| INTMOD
820 	| LOG
821 	| POW
822 	| RSQ
823 	| RSQRTM
824 	| SIN
825 	| SQRT
826 	| SINCOS
827 	;
828 
829 /* NOP instruction */
830 nopinstruction:
831 	NOP
832 	{
833 		brw_NOP(p);
834 	}
835 	;
836 
837 /* Ternary operand instruction */
838 ternaryinstruction:
839 	predicate ternaryopcodes saturate cond_mod execsize dst srcimm src srcimm instoptions
840 	{
841 		brw_set_default_access_mode(p, $10.access_mode);
842 		i965_asm_ternary_instruction($2, p, $6, $7, $8, $9);
843 		brw_pop_insn_state(p);
844 		i965_asm_set_instruction_options(p, $10);
845 		brw_eu_inst_set_cond_modifier(p->devinfo, brw_last_inst,
846 					   $4.cond_modifier);
847 
848 		if (p->devinfo->ver < 12) {
849 			brw_eu_inst_set_3src_a16_flag_reg_nr(p->devinfo, brw_last_inst,
850 					         $4.flag_reg_nr);
851 			brw_eu_inst_set_3src_a16_flag_subreg_nr(p->devinfo, brw_last_inst,
852 						    $4.flag_subreg_nr);
853 		}
854 
855 		brw_eu_inst_set_saturate(p->devinfo, brw_last_inst, $3);
856 		brw_eu_inst_set_exec_size(p->devinfo, brw_last_inst, $5);
857 		brw_eu_inst_set_group(p->devinfo, brw_last_inst, $10.chan_offset);
858 	}
859 	;
860 
861 ternaryopcodes:
862 	CSEL
863 	| BFE
864 	| BFI2
865 	| LRP
866 	| MAD
867 	| DP4A
868 	| ADD3
869 	;
870 
871 /* Wait instruction */
872 waitinstruction:
873 	WAIT execsize dst instoptions
874 	{
875 		brw_next_insn(p, $1);
876 		i965_asm_set_instruction_options(p, $4);
877 		brw_eu_inst_set_exec_size(p->devinfo, brw_last_inst, $2);
878 		brw_set_default_access_mode(p, $4.access_mode);
879 		struct brw_reg dest = $3;
880 		dest.swizzle = brw_swizzle_for_mask(dest.writemask);
881 		if (dest.file != ARF || dest.nr != BRW_ARF_NOTIFICATION_COUNT)
882 			error(&@1, "WAIT must use the notification register\n");
883 		brw_set_dest(p, brw_last_inst, dest);
884 		brw_set_src0(p, brw_last_inst, dest);
885 		brw_set_src1(p, brw_last_inst, brw_null_reg());
886 		brw_eu_inst_set_mask_control(p->devinfo, brw_last_inst, BRW_MASK_DISABLE);
887 	}
888 	;
889 
890 /* Send instruction */
891 sendinstruction:
892 	predicate sendopcode execsize dst payload exp2 sharedfunction msgdesc instoptions
893 	{
894 		i965_asm_set_instruction_options(p, $9);
895 		brw_eu_inst_set_exec_size(p->devinfo, brw_last_inst, $3);
896 		brw_set_dest(p, brw_last_inst, $4);
897 		brw_set_src0(p, brw_last_inst, $5);
898 		brw_eu_inst_set_bits(brw_last_inst, 127, 96, $6);
899 		brw_eu_inst_set_src1_file_type(p->devinfo, brw_last_inst,
900 				            IMM,
901 					    BRW_TYPE_UD);
902 		brw_eu_inst_set_sfid(p->devinfo, brw_last_inst, $7);
903 		brw_eu_inst_set_eot(p->devinfo, brw_last_inst, $9.end_of_thread);
904 		brw_eu_inst_set_group(p->devinfo, brw_last_inst, $9.chan_offset);
905 
906 		brw_pop_insn_state(p);
907 	}
908 	| predicate sendopcode execsize dst payload payload exp2 sharedfunction msgdesc instoptions
909 	{
910 		assert(p->devinfo->ver < 12);
911 
912 		i965_asm_set_instruction_options(p, $10);
913 		brw_eu_inst_set_exec_size(p->devinfo, brw_last_inst, $3);
914 		brw_set_dest(p, brw_last_inst, $4);
915 		brw_set_src0(p, brw_last_inst, $5);
916 		brw_eu_inst_set_bits(brw_last_inst, 127, 96, $7);
917 		brw_eu_inst_set_sfid(p->devinfo, brw_last_inst, $8);
918 		brw_eu_inst_set_eot(p->devinfo, brw_last_inst, $10.end_of_thread);
919 		brw_eu_inst_set_group(p->devinfo, brw_last_inst, $10.chan_offset);
920 
921 		brw_pop_insn_state(p);
922 	}
923 	| predicate sendsopcode execsize dst payload payload desc ex_desc sharedfunction msgdesc instoptions
924 	{
925 		i965_asm_set_instruction_options(p, $11);
926 		brw_eu_inst_set_exec_size(p->devinfo, brw_last_inst, $3);
927 		brw_set_dest(p, brw_last_inst, $4);
928 		brw_set_src0(p, brw_last_inst, $5);
929 		brw_set_src1(p, brw_last_inst, $6);
930 
931 		if ($7.file == IMM) {
932 			brw_eu_inst_set_send_sel_reg32_desc(p->devinfo, brw_last_inst, 0);
933 			brw_eu_inst_set_send_desc(p->devinfo, brw_last_inst, $7.ud);
934 		} else {
935 			brw_eu_inst_set_send_sel_reg32_desc(p->devinfo, brw_last_inst, 1);
936 		}
937 
938 		if ($8.file == IMM) {
939 			brw_eu_inst_set_send_sel_reg32_ex_desc(p->devinfo, brw_last_inst, 0);
940 			brw_eu_inst_set_sends_ex_desc(p->devinfo, brw_last_inst, $8.ud, false);
941 		} else {
942 			brw_eu_inst_set_send_sel_reg32_ex_desc(p->devinfo, brw_last_inst, 1);
943 			brw_eu_inst_set_send_ex_desc_ia_subreg_nr(p->devinfo, brw_last_inst, $8.subnr >> 2);
944 		}
945 
946 		brw_eu_inst_set_sfid(p->devinfo, brw_last_inst, $9);
947 		brw_eu_inst_set_eot(p->devinfo, brw_last_inst, $11.end_of_thread);
948 		brw_eu_inst_set_group(p->devinfo, brw_last_inst, $11.chan_offset);
949 
950 		if (p->devinfo->verx10 >= 125 && $10.ex_bso) {
951 			brw_eu_inst_set_send_ex_bso(p->devinfo, brw_last_inst, 1);
952 			brw_eu_inst_set_send_src1_len(p->devinfo, brw_last_inst,
953 						   $10.src1_len);
954 		}
955 
956 		brw_pop_insn_state(p);
957 	}
958 	| predicate sendsopcode execsize dst GENREGFILE LSQUARE scalarreg RSQUARE desc ex_desc sharedfunction msgdesc instoptions
959 	{
960                 assert(p->devinfo->ver >= 30);
961 
962 		i965_asm_set_instruction_options(p, $13);
963 		brw_eu_inst_set_exec_size(p->devinfo, brw_last_inst, $3);
964 		brw_set_dest(p, brw_last_inst, $4);
965 		brw_set_src0(p, brw_last_inst, $7);
966 		brw_set_src1(p, brw_last_inst, brw_null_reg());
967 
968 		if ($9.file == IMM) {
969 			brw_eu_inst_set_send_sel_reg32_desc(p->devinfo, brw_last_inst, 0);
970 			brw_eu_inst_set_send_desc(p->devinfo, brw_last_inst, $9.ud);
971 		} else {
972 			brw_eu_inst_set_send_sel_reg32_desc(p->devinfo, brw_last_inst, 1);
973 		}
974 
975 		if ($10.file == IMM) {
976 			brw_eu_inst_set_send_sel_reg32_ex_desc(p->devinfo, brw_last_inst, 0);
977 			brw_eu_inst_set_sends_ex_desc(p->devinfo, brw_last_inst, $10.ud, true);
978 		} else {
979 			brw_eu_inst_set_send_sel_reg32_ex_desc(p->devinfo, brw_last_inst, 1);
980 			brw_eu_inst_set_send_ex_desc_ia_subreg_nr(p->devinfo, brw_last_inst, $10.subnr >> 2);
981 		}
982 
983 		brw_eu_inst_set_sfid(p->devinfo, brw_last_inst, $11);
984 		brw_eu_inst_set_eot(p->devinfo, brw_last_inst, $13.end_of_thread);
985 		brw_eu_inst_set_group(p->devinfo, brw_last_inst, $13.chan_offset);
986 
987 		if ($12.ex_bso) {
988 			brw_eu_inst_set_send_ex_bso(p->devinfo, brw_last_inst, 1);
989                         /* Not settings src1 length, as its implied zero. */
990 		}
991 
992 		brw_pop_insn_state(p);
993 	}
994 	;
995 
996 sendop:
997 	SEND_GFX4
998 	| SENDC_GFX4
999 	;
1000 
1001 sendsop:
1002 	SEND_GFX12
1003 	| SENDC_GFX12
1004 	| SENDS
1005 	| SENDSC
1006 	;
1007 
1008 sendopcode:
1009 	sendop   { $$ = brw_next_insn(p, $1); }
1010 	;
1011 
1012 sendsopcode:
1013 	sendsop  { $$ = brw_next_insn(p, $1); }
1014 	;
1015 
1016 sharedfunction:
1017 	NULL_TOKEN 	        { $$ = BRW_SFID_NULL; }
1018 	| GATEWAY 	        { $$ = BRW_SFID_MESSAGE_GATEWAY; }
1019 	| URB 		        { $$ = BRW_SFID_URB; }
1020 	| THREAD_SPAWNER 	{ $$ = BRW_SFID_THREAD_SPAWNER; }
1021 	| VME 		        { $$ = BRW_SFID_VME; }
1022 	| RENDER 	        { $$ = GFX6_SFID_DATAPORT_RENDER_CACHE; }
1023 	| CONST 	        { $$ = GFX6_SFID_DATAPORT_CONSTANT_CACHE; }
1024 	| DATA 		        { $$ = GFX7_SFID_DATAPORT_DATA_CACHE; }
1025 	| PIXEL_INTERP 	        { $$ = GFX7_SFID_PIXEL_INTERPOLATOR; }
1026 	| DP_DATA_1 	        { $$ = HSW_SFID_DATAPORT_DATA_CACHE_1; }
1027 	| CRE 		        { $$ = HSW_SFID_CRE; }
1028 	| SAMPLER	        { $$ = BRW_SFID_SAMPLER; }
1029 	| DP_SAMPLER	        { $$ = GFX6_SFID_DATAPORT_SAMPLER_CACHE; }
1030 	| RT_ACCEL		{ $$ = GEN_RT_SFID_RAY_TRACE_ACCELERATOR; }
1031 	| SLM			{ $$ = GFX12_SFID_SLM; }
1032 	| TGM			{ $$ = GFX12_SFID_TGM; }
1033 	| UGM			{ $$ = GFX12_SFID_UGM; }
1034 	;
1035 
1036 exp2:
1037 	LONG 		{ $$ = $1; }
1038 	| MINUS LONG 	{ $$ = -$2; }
1039 	;
1040 
1041 desc:
1042 	reg32a
1043 	| exp2
1044 	{
1045 		$$ = brw_imm_ud($1);
1046 	}
1047 	;
1048 
1049 ex_desc:
1050 	reg32a
1051 	| exp2
1052 	{
1053 		$$ = brw_imm_ud($1);
1054 	}
1055 	;
1056 
1057 reg32a:
1058 	addrreg region reg_type
1059 	{
1060 		$$ = set_direct_src_operand(&$1, $3);
1061 		$$ = stride($$, $2.vstride, $2.width, $2.hstride);
1062 	}
1063 	;
1064 
1065 
1066 /* Jump instruction */
1067 jumpinstruction:
1068 	predicate JMPI execsize relativelocation2 instoptions
1069 	{
1070 		brw_next_insn(p, $2);
1071 		i965_asm_set_instruction_options(p, $5);
1072 		brw_eu_inst_set_exec_size(p->devinfo, brw_last_inst, $3);
1073 		brw_set_dest(p, brw_last_inst, brw_ip_reg());
1074 		brw_set_src0(p, brw_last_inst, brw_ip_reg());
1075 		brw_set_src1(p, brw_last_inst, $4);
1076 		brw_eu_inst_set_pred_control(p->devinfo, brw_last_inst,
1077 					  brw_eu_inst_pred_control(p->devinfo,
1078 								brw_last_inst));
1079 		brw_pop_insn_state(p);
1080 	}
1081 	;
1082 
1083 /* branch instruction */
1084 branchinstruction:
1085 	predicate ENDIF execsize JUMP_LABEL instoptions
1086 	{
1087 		add_label(p, $4, INSTR_LABEL_JIP);
1088 
1089 		brw_next_insn(p, $2);
1090 		i965_asm_set_instruction_options(p, $5);
1091 		brw_eu_inst_set_exec_size(p->devinfo, brw_last_inst, $3);
1092 
1093 		brw_set_src0(p, brw_last_inst, brw_imm_d(0x0));
1094 
1095 		brw_pop_insn_state(p);
1096 	}
1097 	| ELSE execsize JUMP_LABEL jumplabel instoptions
1098 	{
1099 		add_label(p, $3, INSTR_LABEL_JIP);
1100 		add_label(p, $4, INSTR_LABEL_UIP);
1101 
1102 		brw_next_insn(p, $1);
1103 		i965_asm_set_instruction_options(p, $5);
1104 		brw_eu_inst_set_exec_size(p->devinfo, brw_last_inst, $2);
1105 
1106 		brw_set_dest(p, brw_last_inst, retype(brw_null_reg(),
1107 			     BRW_TYPE_D));
1108 		if (p->devinfo->ver < 12)
1109 			brw_set_src0(p, brw_last_inst, brw_imm_d(0));
1110 	}
1111 	| predicate IF execsize JUMP_LABEL jumplabel instoptions
1112 	{
1113 		add_label(p, $4, INSTR_LABEL_JIP);
1114 		add_label(p, $5, INSTR_LABEL_UIP);
1115 
1116 		brw_next_insn(p, $2);
1117 		i965_asm_set_instruction_options(p, $6);
1118 		brw_eu_inst_set_exec_size(p->devinfo, brw_last_inst, $3);
1119 
1120 		brw_set_dest(p, brw_last_inst,
1121 			     vec1(retype(brw_null_reg(),
1122 			     BRW_TYPE_D)));
1123 		if (p->devinfo->ver < 12)
1124 			brw_set_src0(p, brw_last_inst, brw_imm_d(0x0));
1125 
1126 		brw_pop_insn_state(p);
1127 	}
1128 	;
1129 
1130 /* break instruction */
1131 breakinstruction:
1132 	predicate BREAK execsize JUMP_LABEL JUMP_LABEL instoptions
1133 	{
1134 		add_label(p, $4, INSTR_LABEL_JIP);
1135 		add_label(p, $5, INSTR_LABEL_UIP);
1136 
1137 		brw_next_insn(p, $2);
1138 		i965_asm_set_instruction_options(p, $6);
1139 		brw_eu_inst_set_exec_size(p->devinfo, brw_last_inst, $3);
1140 
1141 		brw_set_dest(p, brw_last_inst, retype(brw_null_reg(),
1142 			     BRW_TYPE_D));
1143 		brw_set_src0(p, brw_last_inst, brw_imm_d(0x0));
1144 
1145 		brw_pop_insn_state(p);
1146 	}
1147 	| predicate HALT execsize JUMP_LABEL JUMP_LABEL instoptions
1148 	{
1149 		add_label(p, $4, INSTR_LABEL_JIP);
1150 		add_label(p, $5, INSTR_LABEL_UIP);
1151 
1152 		brw_next_insn(p, $2);
1153 		i965_asm_set_instruction_options(p, $6);
1154 		brw_eu_inst_set_exec_size(p->devinfo, brw_last_inst, $3);
1155 
1156 		brw_set_dest(p, brw_last_inst, retype(brw_null_reg(),
1157 			     BRW_TYPE_D));
1158 
1159 		if (p->devinfo->ver < 12) {
1160 			brw_set_src0(p, brw_last_inst, brw_imm_d(0x0));
1161 		}
1162 
1163 		brw_pop_insn_state(p);
1164 	}
1165 	| predicate CONT execsize JUMP_LABEL JUMP_LABEL instoptions
1166 	{
1167 		add_label(p, $4, INSTR_LABEL_JIP);
1168 		add_label(p, $5, INSTR_LABEL_UIP);
1169 
1170 		brw_next_insn(p, $2);
1171 		i965_asm_set_instruction_options(p, $6);
1172 		brw_eu_inst_set_exec_size(p->devinfo, brw_last_inst, $3);
1173 		brw_set_dest(p, brw_last_inst, brw_ip_reg());
1174 
1175 		brw_set_src0(p, brw_last_inst, brw_imm_d(0x0));
1176 
1177 		brw_pop_insn_state(p);
1178 	}
1179 	;
1180 
1181 /* loop instruction */
1182 loopinstruction:
1183 	predicate WHILE execsize JUMP_LABEL instoptions
1184 	{
1185 		add_label(p, $4, INSTR_LABEL_JIP);
1186 
1187 		brw_next_insn(p, $2);
1188 		i965_asm_set_instruction_options(p, $5);
1189 		brw_eu_inst_set_exec_size(p->devinfo, brw_last_inst, $3);
1190 
1191 		brw_set_dest(p, brw_last_inst,
1192 					retype(brw_null_reg(),
1193 					BRW_TYPE_D));
1194 		if (p->devinfo->ver < 12)
1195 			brw_set_src0(p, brw_last_inst, brw_imm_d(0x0));
1196 
1197 		brw_pop_insn_state(p);
1198 	}
1199 	| DO execsize instoptions
1200 	{
1201 		brw_next_insn(p, $1);
1202 	}
1203 	;
1204 
1205 /* sync instruction */
1206 syncinstruction:
1207 	predicate SYNC sync_function execsize sync_arg instoptions
1208 	{
1209 		if (p->devinfo->ver < 12) {
1210 			error(&@2, "sync instruction is supported only on gfx12+\n");
1211 		}
1212 
1213 		if ($5.file == IMM &&
1214 		    $3 != TGL_SYNC_ALLRD &&
1215 		    $3 != TGL_SYNC_ALLWR) {
1216 			error(&@2, "Only allrd and allwr support immediate argument\n");
1217 		}
1218 
1219 		brw_set_default_access_mode(p, $6.access_mode);
1220 		brw_SYNC(p, $3);
1221 		i965_asm_set_instruction_options(p, $6);
1222 		brw_eu_inst_set_exec_size(p->devinfo, brw_last_inst, $4);
1223 		brw_set_src0(p, brw_last_inst, $5);
1224 		brw_eu_inst_set_eot(p->devinfo, brw_last_inst, $6.end_of_thread);
1225 		brw_eu_inst_set_group(p->devinfo, brw_last_inst, $6.chan_offset);
1226 
1227 		brw_pop_insn_state(p);
1228 	}
1229 	;
1230 
1231 sync_function:
1232 	NOP		{ $$ = TGL_SYNC_NOP; }
1233 	| ALLRD
1234 	| ALLWR
1235 	| FENCE
1236 	| BAR
1237 	| HOST
1238 	;
1239 
1240 sync_arg:
1241 	nullreg region reg_type
1242 	{
1243 		$$ = $1;
1244 		$$.vstride = $2.vstride;
1245 		$$.width = $2.width;
1246 		$$.hstride = $2.hstride;
1247 		$$.type = $3;
1248 	}
1249 	| immreg
1250 	;
1251 
1252 /* Relative location */
1253 relativelocation2:
1254 	immreg
1255 	| reg32
1256 	;
1257 
1258 jumplabel:
1259 	JUMP_LABEL	{ $$ = $1; }
1260 	| /* empty */	{ $$ = NULL; }
1261 	;
1262 
1263 jumplabeltarget:
1264 	JUMP_LABEL_TARGET
1265 	{
1266 		struct target_label *label = rzalloc(p->mem_ctx, struct target_label);
1267 
1268 		label->name = ralloc_strdup(p->mem_ctx, $1);
1269 		label->offset = p->next_insn_offset;
1270 
1271 		list_addtail(&label->link, &target_labels);
1272 	}
1273 	;
1274 
1275 /* Destination register */
1276 dst:
1277 	dstoperand
1278 	| dstoperandex
1279 	;
1280 
1281 dstoperand:
1282 	dstreg dstregion writemask reg_type
1283 	{
1284 		$$ = $1;
1285 		$$.vstride = BRW_VERTICAL_STRIDE_1;
1286 		$$.width = BRW_WIDTH_1;
1287 		$$.hstride = $2;
1288 		$$.type = $4;
1289 		$$.writemask = $3;
1290 		$$.swizzle = BRW_SWIZZLE_NOOP;
1291 		$$.subnr = $$.subnr * brw_type_size_bytes($4);
1292 	}
1293 	;
1294 
1295 dstoperandex:
1296 	dstoperandex_typed dstregion writemask reg_type
1297 	{
1298 		$$ = $1;
1299 		$$.hstride = $2;
1300 		$$.type = $4;
1301 		$$.writemask = $3;
1302 		$$.subnr = $$.subnr * brw_type_size_bytes($4);
1303 	}
1304 	/* BSpec says "When the conditional modifier is present, updates
1305 	 * to the selected flag register also occur. In this case, the
1306 	 * register region fields of the ‘null’ operand are valid."
1307 	 */
1308 	| nullreg dstregion writemask reg_type
1309 	{
1310 		$$ = $1;
1311 		$$.vstride = BRW_VERTICAL_STRIDE_1;
1312 		$$.width = BRW_WIDTH_1;
1313 		$$.hstride = $2;
1314 		$$.writemask = $3;
1315 		$$.type = $4;
1316 	}
1317 	| threadcontrolreg
1318 	{
1319 		$$ = $1;
1320 		$$.hstride = 1;
1321 		$$.type = BRW_TYPE_UW;
1322 	}
1323 	;
1324 
1325 dstoperandex_typed:
1326 	accreg
1327 	| addrreg
1328 	| channelenablereg
1329 	| controlreg
1330 	| flagreg
1331 	| ipreg
1332 	| maskreg
1333 	| notifyreg
1334 	| performancereg
1335 	| statereg
1336 	| scalarreg
1337 	;
1338 
1339 dstreg:
1340 	directgenreg
1341 	{
1342 		$$ = $1;
1343 		$$.address_mode = BRW_ADDRESS_DIRECT;
1344 	}
1345 	| indirectgenreg
1346 	{
1347 		$$ = $1;
1348 		$$.address_mode = BRW_ADDRESS_REGISTER_INDIRECT_REGISTER;
1349 	}
1350 	;
1351 
1352 /* Source register */
1353 srcaccimm:
1354 	srcacc
1355 	| immreg
1356 	;
1357 
1358 immreg:
1359 	immval imm_type
1360 	{
1361 		switch ($2) {
1362 		case BRW_TYPE_UD:
1363 			$$ = brw_imm_ud($1);
1364 			break;
1365 		case BRW_TYPE_D:
1366 			$$ = brw_imm_d($1);
1367 			break;
1368 		case BRW_TYPE_UW:
1369 			$$ = brw_imm_uw($1 | ($1 << 16));
1370 			break;
1371 		case BRW_TYPE_W:
1372 			$$ = brw_imm_w($1);
1373 			break;
1374 		case BRW_TYPE_F:
1375 			$$ = brw_imm_reg(BRW_TYPE_F);
1376 			/* Set u64 instead of ud since DIM uses a 64-bit F-typed imm */
1377 			$$.u64 = $1;
1378 			break;
1379 		case BRW_TYPE_V:
1380 			$$ = brw_imm_v($1);
1381 			break;
1382 		case BRW_TYPE_UV:
1383 			$$ = brw_imm_uv($1);
1384 			break;
1385 		case BRW_TYPE_VF:
1386 			$$ = brw_imm_vf($1);
1387 			break;
1388 		case BRW_TYPE_Q:
1389 			$$ = brw_imm_q($1);
1390 			break;
1391 		case BRW_TYPE_UQ:
1392 			$$ = brw_imm_uq($1);
1393 			break;
1394 		case BRW_TYPE_DF:
1395 			$$ = brw_imm_reg(BRW_TYPE_DF);
1396 			$$.d64 = $1;
1397 			break;
1398 		case BRW_TYPE_HF:
1399 			$$ = brw_imm_reg(BRW_TYPE_HF);
1400 			$$.ud = $1 | ($1 << 16);
1401 			break;
1402 		default:
1403 			error(&@2, "Unknown immediate type %s\n",
1404 			      brw_reg_type_to_letters($2));
1405 		}
1406 	}
1407 	;
1408 
1409 reg32:
1410 	directgenreg region reg_type
1411 	{
1412 		$$ = set_direct_src_operand(&$1, $3);
1413 		$$ = stride($$, $2.vstride, $2.width, $2.hstride);
1414 	}
1415 	;
1416 
1417 payload:
1418 	directsrcoperand
1419 	;
1420 
1421 src:
1422 	directsrcoperand
1423 	| indirectsrcoperand
1424 	;
1425 
1426 srcacc:
1427 	directsrcaccoperand
1428 	| indirectsrcoperand
1429 	;
1430 
1431 srcimm:
1432 	directsrcoperand
1433 	| indirectsrcoperand
1434 	| immreg
1435 	;
1436 
1437 directsrcaccoperand:
1438 	directsrcoperand
1439 	| negate abs accreg region reg_type
1440 	{
1441 		$$ = set_direct_src_operand(&$3, $5);
1442 		$$.negate = $1;
1443 		$$.abs = $2;
1444 		$$.vstride = $4.vstride;
1445 		$$.width = $4.width;
1446 		$$.hstride = $4.hstride;
1447 	}
1448 	;
1449 
1450 srcarcoperandex:
1451 	srcarcoperandex_typed region reg_type
1452 	{
1453 		$$ = brw_make_reg($1.file,
1454 			          $1.nr,
1455 			          $1.subnr,
1456 			          0,
1457 			          0,
1458 			          $3,
1459 			          $2.vstride,
1460 			          $2.width,
1461 			          $2.hstride,
1462 			          BRW_SWIZZLE_NOOP,
1463 			          WRITEMASK_XYZW);
1464 	}
1465 	| nullreg region reg_type
1466 	{
1467 		$$ = set_direct_src_operand(&$1, $3);
1468 		$$.vstride = $2.vstride;
1469 		$$.width = $2.width;
1470 		$$.hstride = $2.hstride;
1471 	}
1472 	| threadcontrolreg
1473 	{
1474 		$$ = set_direct_src_operand(&$1, BRW_TYPE_UW);
1475 	}
1476 	;
1477 
1478 srcarcoperandex_typed:
1479 	channelenablereg
1480 	| controlreg
1481 	| flagreg
1482 	| ipreg
1483 	| maskreg
1484 	| statereg
1485 	| scalarreg
1486 	;
1487 
1488 indirectsrcoperand:
1489 	negate abs indirectgenreg indirectregion swizzle reg_type
1490 	{
1491 		$$ = brw_make_reg($3.file,
1492 			          0,
1493 			          $3.subnr,
1494 			          $1,  // negate
1495 			          $2,  // abs
1496 			          $6,
1497 			          $4.vstride,
1498 			          $4.width,
1499 			          $4.hstride,
1500 			          $5,
1501 			          WRITEMASK_X);
1502 
1503 		$$.address_mode = BRW_ADDRESS_REGISTER_INDIRECT_REGISTER;
1504 		// brw_reg set indirect_offset to 0 so set it to valid value
1505 		$$.indirect_offset = $3.indirect_offset;
1506 	}
1507 	;
1508 
1509 directgenreg_list:
1510 	directgenreg
1511 	| notifyreg
1512 	| addrreg
1513 	| performancereg
1514 	;
1515 
1516 directsrcoperand:
1517 	negate abs directgenreg_list region swizzle reg_type
1518 	{
1519 		$$ = brw_make_reg($3.file,
1520 			          $3.nr,
1521 			          $3.subnr,
1522 			          $1,
1523 			          $2,
1524 			          $6,
1525 			          $4.vstride,
1526 			          $4.width,
1527 			          $4.hstride,
1528 			          $5,
1529 			          WRITEMASK_X);
1530 	}
1531 	| srcarcoperandex
1532 	;
1533 
1534 /* Address register */
1535 addrparam:
1536 	addrreg exp
1537 	{
1538 		memset(&$$, '\0', sizeof($$));
1539 		$$.subnr = $1.subnr;
1540 		$$.indirect_offset = $2;
1541 	}
1542 	| addrreg
1543 	;
1544 
1545 /* Register files and register numbers */
1546 exp:
1547 	INTEGER 	{ $$ = $1; }
1548 	| LONG 	        { $$ = $1; }
1549 	;
1550 
1551 subregnum:
1552 	DOT exp 		        { $$ = $2; }
1553 	| /* empty */ %prec SUBREGNUM 	{ $$ = 0; }
1554 	;
1555 
1556 directgenreg:
1557 	GENREG subregnum
1558 	{
1559 		memset(&$$, '\0', sizeof($$));
1560 		$$.file = FIXED_GRF;
1561 		$$.nr = $1 * reg_unit(p->devinfo);
1562 		$$.subnr = $2;
1563 	}
1564 	;
1565 
1566 indirectgenreg:
1567 	GENREGFILE LSQUARE addrparam RSQUARE
1568 	{
1569 		memset(&$$, '\0', sizeof($$));
1570 		$$.file = FIXED_GRF;
1571 		$$.subnr = $3.subnr;
1572 		$$.indirect_offset = $3.indirect_offset;
1573 	}
1574 	;
1575 
1576 addrreg:
1577 	ADDRREG subregnum
1578 	{
1579 		int subnr = 16;
1580 
1581 		if ($2 > subnr)
1582 			error(&@2, "Address sub register number %d"
1583 				   "out of range\n", $2);
1584 
1585 		$$.file = ARF;
1586 		$$.nr = BRW_ARF_ADDRESS;
1587 		$$.subnr = $2;
1588 	}
1589 	;
1590 
1591 accreg:
1592 	ACCREG subregnum
1593 	{
1594 		int nr_reg = 10;
1595 
1596 		if ($1 > nr_reg)
1597 			error(&@1, "Accumulator register number %d"
1598 				   " out of range\n", $1);
1599 
1600 		memset(&$$, '\0', sizeof($$));
1601 		$$.file = ARF;
1602 		$$.nr = BRW_ARF_ACCUMULATOR;
1603 		$$.subnr = $2;
1604 	}
1605 	;
1606 
1607 flagreg:
1608 	FLAGREG subregnum
1609 	{
1610 		// 2 flag reg
1611 		int nr_reg = 2;
1612 		int subnr = nr_reg;
1613 
1614 		if ($1 > nr_reg)
1615 			error(&@1, "Flag register number %d"
1616 				   " out of range \n", $1);
1617 		if ($2 > subnr)
1618 			error(&@2, "Flag subregister number %d"
1619 				   " out of range\n", $2);
1620 
1621 		$$.file = ARF;
1622 		$$.nr = BRW_ARF_FLAG | $1;
1623 		$$.subnr = $2;
1624 	}
1625 	;
1626 
1627 maskreg:
1628 	MASKREG subregnum
1629 	{
1630 		if ($1 > 0)
1631 			error(&@1, "Mask register number %d"
1632 				   " out of range\n", $1);
1633 
1634 		$$.file = ARF;
1635 		$$.nr = BRW_ARF_MASK;
1636 		$$.subnr = $2;
1637 	}
1638 	;
1639 
1640 notifyreg:
1641 	NOTIFYREG subregnum
1642 	{
1643 		int subnr = (p->devinfo->ver >= 11) ? 2 : 3;
1644 		if ($2 > subnr)
1645 			error(&@2, "Notification sub register number %d"
1646 				   " out of range\n", $2);
1647 
1648 		$$.file = ARF;
1649 		$$.nr = BRW_ARF_NOTIFICATION_COUNT;
1650 		$$.subnr = $2;
1651 	}
1652 	;
1653 
1654 scalarreg:
1655 	SCALARREG subregnum
1656 	{
1657 		if ($2 > 31)
1658 			error(&@2, "Scalar sub register number %d"
1659 			           " out of range\n", $2);
1660 
1661 		$$.file = ARF;
1662 		$$.nr = BRW_ARF_SCALAR;
1663 		$$.subnr = $2;
1664 	}
1665 
1666 statereg:
1667 	STATEREG subregnum
1668 	{
1669 		if ($1 > 2)
1670 			error(&@1, "State register number %d"
1671 				   " out of range\n", $1);
1672 
1673 		if ($2 > 4)
1674 			error(&@2, "State sub register number %d"
1675 				   " out of range\n", $2);
1676 
1677 		$$.file = ARF;
1678 		$$.nr = BRW_ARF_STATE;
1679 		$$.subnr = $2;
1680 	}
1681 	;
1682 
1683 controlreg:
1684 	CONTROLREG subregnum
1685 	{
1686 		if ($2 > 3)
1687 			error(&@2, "control sub register number %d"
1688 				   " out of range\n", $2);
1689 
1690 		$$.file = ARF;
1691 		$$.nr = BRW_ARF_CONTROL;
1692 		$$.subnr = $2;
1693 	}
1694 	;
1695 
1696 ipreg:
1697 	IPREG		{ $$ = brw_ip_reg(); }
1698 	;
1699 
1700 nullreg:
1701 	NULL_TOKEN 	{ $$ = brw_null_reg(); }
1702 	;
1703 
1704 threadcontrolreg:
1705 	THREADREG subregnum
1706 	{
1707 		if ($2 > 7)
1708 			error(&@2, "Thread control sub register number %d"
1709 				   " out of range\n", $2);
1710 
1711 		$$.file = ARF;
1712 		$$.nr = BRW_ARF_TDR;
1713 		$$.subnr = $2;
1714 	}
1715 	;
1716 
1717 performancereg:
1718 	PERFORMANCEREG subregnum
1719 	{
1720 		int subnr;
1721 		if (p->devinfo->ver >= 10)
1722 			subnr = 5;
1723 		else
1724 			subnr = 4;
1725 
1726 		if ($2 > subnr)
1727 			error(&@2, "Performance sub register number %d"
1728 				   " out of range\n", $2);
1729 
1730 		$$.file = ARF;
1731 		$$.nr = BRW_ARF_TIMESTAMP;
1732 		$$.subnr = $2;
1733 	}
1734 	;
1735 
1736 channelenablereg:
1737 	CHANNELENABLEREG subregnum
1738 	{
1739 		if ($1 > 0)
1740 			error(&@1, "Channel enable register number %d"
1741 				   " out of range\n", $1);
1742 
1743 		$$.file = ARF;
1744 		$$.nr = BRW_ARF_MASK;
1745 		$$.subnr = $2;
1746 	}
1747 	;
1748 
1749 /* Immediate values */
1750 immval:
1751 	exp2
1752 	{
1753 		$$ = $1;
1754 	}
1755 	| LSQUARE exp2 COMMA exp2 COMMA exp2 COMMA exp2 RSQUARE
1756 	{
1757 		$$ = ($2 << 0) | ($4 << 8) | ($6 << 16) | ($8 << 24);
1758 	}
1759 	;
1760 
1761 /* Regions */
1762 dstregion:
1763 	/* empty */
1764 	{
1765 		$$ = BRW_HORIZONTAL_STRIDE_1;
1766 	}
1767 	| LANGLE exp RANGLE
1768 	{
1769 		if ($2 != 0 && ($2 > 4 || !isPowerofTwo($2)))
1770 			error(&@2, "Invalid Horizontal stride %d\n", $2);
1771 
1772 		$$ = ffs($2);
1773 	}
1774 	;
1775 
1776 indirectregion:
1777 	region
1778 	| region_wh
1779 	;
1780 
1781 region:
1782 	/* empty */
1783 	{
1784 		$$ = stride($$, 0, 1, 0);
1785 	}
1786 	| LANGLE exp RANGLE
1787 	{
1788 		if ($2 != 0 && ($2 > 32 || !isPowerofTwo($2)))
1789 			error(&@2, "Invalid VertStride %d\n", $2);
1790 
1791 		$$ = stride($$, $2, 1, 0);
1792 	}
1793 	| LANGLE exp COMMA exp COMMA exp RANGLE
1794 	{
1795 
1796 		if ($2 != 0 && ($2 > 32 || !isPowerofTwo($2)))
1797 			error(&@2, "Invalid VertStride %d\n", $2);
1798 
1799 		if ($4 > 16 || !isPowerofTwo($4))
1800 			error(&@4, "Invalid width %d\n", $4);
1801 
1802 		if ($6 != 0 && ($6 > 4 || !isPowerofTwo($6)))
1803 			error(&@6, "Invalid Horizontal stride in"
1804 				   "  region_wh %d\n", $6);
1805 
1806 		$$ = stride($$, $2, $4, $6);
1807 	}
1808 	| LANGLE exp SEMICOLON exp COMMA exp RANGLE
1809 	{
1810 		if ($2 != 0 && ($2 > 32 || !isPowerofTwo($2)))
1811 			error(&@2, "Invalid VertStride %d\n", $2);
1812 
1813 		if ($4 > 16 || !isPowerofTwo($4))
1814 			error(&@4, "Invalid width %d\n", $4);
1815 
1816 		if ($6 != 0 && ($6 > 4 || !isPowerofTwo($6)))
1817 			error(&@6, "Invalid Horizontal stride in"
1818 				   " region_wh %d\n", $6);
1819 
1820 		$$ = stride($$, $2, $4, $6);
1821 	}
1822 	| LANGLE VxH COMMA exp COMMA exp RANGLE
1823 	{
1824 		if ($4 > 16 || !isPowerofTwo($4))
1825 			error(&@4, "Invalid width %d\n", $4);
1826 
1827 		if ($6 != 0 && ($6 > 4 || !isPowerofTwo($6)))
1828 			error(&@6, "Invalid Horizontal stride in"
1829 				   " region_wh %d\n", $6);
1830 
1831 		$$ = brw_VxH_indirect(0, 0);
1832 	}
1833 	;
1834 
1835 region_wh:
1836 	LANGLE exp COMMA exp RANGLE
1837 	{
1838 		if ($2 > 16 || !isPowerofTwo($2))
1839 			error(&@2, "Invalid width %d\n", $2);
1840 
1841 		if ($4 != 0 && ($4 > 4 || !isPowerofTwo($4)))
1842 			error(&@4, "Invalid Horizontal stride in"
1843 				   " region_wh %d\n", $4);
1844 
1845 		$$ = stride($$, 0, $2, $4);
1846 		$$.vstride = BRW_VERTICAL_STRIDE_ONE_DIMENSIONAL;
1847 	}
1848 	;
1849 
1850 reg_type:
1851 	  TYPE_F 	{ $$ = BRW_TYPE_F;  }
1852 	| TYPE_UD 	{ $$ = BRW_TYPE_UD; }
1853 	| TYPE_D 	{ $$ = BRW_TYPE_D;  }
1854 	| TYPE_UW 	{ $$ = BRW_TYPE_UW; }
1855 	| TYPE_W 	{ $$ = BRW_TYPE_W;  }
1856 	| TYPE_UB 	{ $$ = BRW_TYPE_UB; }
1857 	| TYPE_B 	{ $$ = BRW_TYPE_B;  }
1858 	| TYPE_DF 	{ $$ = BRW_TYPE_DF; }
1859 	| TYPE_UQ 	{ $$ = BRW_TYPE_UQ; }
1860 	| TYPE_Q 	{ $$ = BRW_TYPE_Q;  }
1861 	| TYPE_HF 	{ $$ = BRW_TYPE_HF; }
1862 	;
1863 
1864 imm_type:
1865 	reg_type 	{ $$ = $1; }
1866 	| TYPE_V 	{ $$ = BRW_TYPE_V;  }
1867 	| TYPE_VF 	{ $$ = BRW_TYPE_VF; }
1868 	| TYPE_UV 	{ $$ = BRW_TYPE_UV; }
1869 	;
1870 
1871 writemask:
1872 	/* empty */
1873 	{
1874 		$$ = WRITEMASK_XYZW;
1875 	}
1876 	| DOT writemask_x writemask_y writemask_z writemask_w
1877 	{
1878 		$$ = $2 | $3 | $4 | $5;
1879 	}
1880 	;
1881 
1882 writemask_x:
1883 	/* empty */ 	{ $$ = 0; }
1884 	| X 	{ $$ = 1 << BRW_CHANNEL_X; }
1885 	;
1886 
1887 writemask_y:
1888 	/* empty */ 	{ $$ = 0; }
1889 	| Y 	{ $$ = 1 << BRW_CHANNEL_Y; }
1890 	;
1891 
1892 writemask_z:
1893 	/* empty */ 	{ $$ = 0; }
1894 	| Z 	{ $$ = 1 << BRW_CHANNEL_Z; }
1895 	;
1896 
1897 writemask_w:
1898 	/* empty */ 	{ $$ = 0; }
1899 	| W 	{ $$ = 1 << BRW_CHANNEL_W; }
1900 	;
1901 
1902 swizzle:
1903 	/* empty */
1904 	{
1905 		$$ = BRW_SWIZZLE_NOOP;
1906 	}
1907 	| DOT chansel
1908 	{
1909 		$$ = BRW_SWIZZLE4($2, $2, $2, $2);
1910 	}
1911 	| DOT chansel chansel chansel chansel
1912 	{
1913 		$$ = BRW_SWIZZLE4($2, $3, $4, $5);
1914 	}
1915 	;
1916 
1917 chansel:
1918 	X
1919 	| Y
1920 	| Z
1921 	| W
1922 	;
1923 
1924 /* Instruction prediction and modifiers */
1925 predicate:
1926 	/* empty */
1927 	{
1928 		brw_push_insn_state(p);
1929 		brw_set_default_predicate_control(p, BRW_PREDICATE_NONE);
1930 		brw_set_default_flag_reg(p, 0, 0);
1931 		brw_set_default_predicate_inverse(p, false);
1932 	}
1933 	| LPAREN predstate flagreg predctrl RPAREN
1934 	{
1935 		brw_push_insn_state(p);
1936 		brw_set_default_predicate_inverse(p, $2);
1937 		brw_set_default_flag_reg(p, $3.nr, $3.subnr);
1938 		brw_set_default_predicate_control(p, $4);
1939 	}
1940 	;
1941 
1942 predstate:
1943 	/* empty */     { $$ = 0; }
1944 	| PLUS 	        { $$ = 0; }
1945 	| MINUS 	{ $$ = 1; }
1946 	;
1947 
1948 predctrl:
1949 	/* empty */ 	{ $$ = BRW_PREDICATE_NORMAL; }
1950 	| DOT X 	{ $$ = BRW_PREDICATE_ALIGN16_REPLICATE_X; }
1951 	| DOT Y 	{ $$ = BRW_PREDICATE_ALIGN16_REPLICATE_Y; }
1952 	| DOT Z 	{ $$ = BRW_PREDICATE_ALIGN16_REPLICATE_Z; }
1953 	| DOT W 	{ $$ = BRW_PREDICATE_ALIGN16_REPLICATE_W; }
1954 	| ANYV
1955 	| ALLV
1956 	| ANY2H
1957 	| ALL2H
1958 	| ANY4H
1959 	| ALL4H
1960 	| ANY8H
1961 	| ALL8H
1962 	| ANY16H
1963 	| ALL16H
1964 	| ANY32H
1965 	| ALL32H
1966 	;
1967 
1968 /* Source Modification */
1969 negate:
1970 	/* empty */	{ $$ = 0; }
1971 	| MINUS 	{ $$ = 1; }
1972 	;
1973 
1974 abs:
1975 	/* empty */ 	{ $$ = 0; }
1976 	| ABS 	{ $$ = 1; }
1977 	;
1978 
1979 /* Flag (Conditional) Modifier */
1980 cond_mod:
1981 	condModifiers
1982 	{
1983 		$$.cond_modifier = $1;
1984 		$$.flag_reg_nr = 0;
1985 		$$.flag_subreg_nr = 0;
1986 	}
1987 	| condModifiers DOT flagreg
1988 	{
1989 		$$.cond_modifier = $1;
1990 		$$.flag_reg_nr = $3.nr;
1991 		$$.flag_subreg_nr = $3.subnr;
1992 	}
1993 	;
1994 
1995 condModifiers:
1996 	/* empty */ 	{ $$ = BRW_CONDITIONAL_NONE; }
1997 	| ZERO
1998 	| EQUAL
1999 	| NOT_ZERO
2000 	| NOT_EQUAL
2001 	| GREATER
2002 	| GREATER_EQUAL
2003 	| LESS
2004 	| LESS_EQUAL
2005 	| OVERFLOW
2006 	| ROUND_INCREMENT
2007 	| UNORDERED
2008 	;
2009 
2010 /* message details for send */
2011 msgdesc:
2012 	MSGDESC_BEGIN msgdesc_parts MSGDESC_END { $$ = $2; }
2013 	;
2014 
2015 msgdesc_parts:
2016 	SRC1_LEN ASSIGN INTEGER msgdesc_parts
2017 	{
2018 		$$ = $4;
2019 		$$.src1_len = $3;
2020 	}
2021 	| EX_BSO msgdesc_parts
2022 	{
2023 		$$ = $2;
2024 		$$.ex_bso = 1;
2025 	}
2026 	| INTEGER msgdesc_parts { $$ = $2; }
2027 	| ASSIGN msgdesc_parts { $$ = $2; }
2028 	| /* empty */
2029 	{
2030 		memset(&$$, 0, sizeof($$));
2031 	}
2032 	;
2033 
2034 saturate:
2035 	/* empty */ 	{ $$ = BRW_INSTRUCTION_NORMAL; }
2036 	| SATURATE 	{ $$ = BRW_INSTRUCTION_SATURATE; }
2037 	;
2038 
2039 /* Execution size */
2040 execsize:
2041 	/* empty */ %prec EMPTYEXECSIZE
2042 	{
2043 		$$ = 0;
2044 	}
2045 	| LPAREN exp2 RPAREN
2046 	{
2047 		if ($2 > 32 || !isPowerofTwo($2))
2048 			error(&@2, "Invalid execution size %llu\n", $2);
2049 
2050 		$$ = cvt($2) - 1;
2051 	}
2052 	;
2053 
2054 /* Instruction options */
2055 instoptions:
2056 	/* empty */
2057 	{
2058 		memset(&$$, 0, sizeof($$));
2059 	}
2060 	| LCURLY instoption_list RCURLY
2061 	{
2062 		memset(&$$, 0, sizeof($$));
2063 		$$ = $2;
2064 	}
2065 	;
2066 
2067 instoption_list:
2068 	instoption_list COMMA instoption
2069 	{
2070 		memset(&$$, 0, sizeof($$));
2071 		$$ = $1;
2072 		add_instruction_option(&$$, $3);
2073 	}
2074 	| instoption_list instoption
2075 	{
2076 		memset(&$$, 0, sizeof($$));
2077 		$$ = $1;
2078 		add_instruction_option(&$$, $2);
2079 	}
2080 	| /* empty */
2081 	{
2082 		memset(&$$, 0, sizeof($$));
2083 	}
2084 	;
2085 
2086 depinfo:
2087 	REG_DIST_CURRENT
2088 	{
2089 		memset(&$$, 0, sizeof($$));
2090 		$$.regdist = $1;
2091 		$$.pipe = TGL_PIPE_NONE;
2092 	}
2093 	| REG_DIST_FLOAT
2094 	{
2095 		memset(&$$, 0, sizeof($$));
2096 		$$.regdist = $1;
2097 		$$.pipe = TGL_PIPE_FLOAT;
2098 	}
2099 	| REG_DIST_INT
2100 	{
2101 		memset(&$$, 0, sizeof($$));
2102 		$$.regdist = $1;
2103 		$$.pipe = TGL_PIPE_INT;
2104 	}
2105 	| REG_DIST_LONG
2106 	{
2107 		memset(&$$, 0, sizeof($$));
2108 		$$.regdist = $1;
2109 		$$.pipe = TGL_PIPE_LONG;
2110 	}
2111 	| REG_DIST_ALL
2112 	{
2113 		memset(&$$, 0, sizeof($$));
2114 		$$.regdist = $1;
2115 		$$.pipe = TGL_PIPE_ALL;
2116 	}
2117 	| REG_DIST_MATH
2118 	{
2119 		memset(&$$, 0, sizeof($$));
2120 		$$.regdist = $1;
2121 		$$.pipe = TGL_PIPE_MATH;
2122 	}
2123 	| REG_DIST_SCALAR
2124 	{
2125 		memset(&$$, 0, sizeof($$));
2126 		$$.regdist = $1;
2127 		$$.pipe = TGL_PIPE_SCALAR;
2128 	}
2129 	| SBID_ALLOC
2130 	{
2131 		memset(&$$, 0, sizeof($$));
2132 		$$.sbid = $1;
2133 		$$.mode = TGL_SBID_SET;
2134 	}
2135 	| SBID_WAIT_SRC
2136 	{
2137 		memset(&$$, 0, sizeof($$));
2138 		$$.sbid = $1;
2139 		$$.mode = TGL_SBID_SRC;
2140 	}
2141 	| SBID_WAIT_DST
2142 	{
2143 		memset(&$$, 0, sizeof($$));
2144 		$$.sbid = $1;
2145 		$$.mode = TGL_SBID_DST;
2146 	}
2147 
2148 instoption:
2149 	ALIGN1 	        { $$.type = INSTOPTION_FLAG; $$.uint_value = ALIGN1;}
2150 	| ALIGN16 	{ $$.type = INSTOPTION_FLAG; $$.uint_value = ALIGN16; }
2151 	| ACCWREN
2152 	{
2153 		if (p->devinfo->ver >= 20)
2154 			error(&@1, "AccWrEnable not supported in Xe2+\n");
2155 		$$.type = INSTOPTION_FLAG;
2156 		$$.uint_value = ACCWREN;
2157 	}
2158 	| BREAKPOINT 	{ $$.type = INSTOPTION_FLAG; $$.uint_value = BREAKPOINT; }
2159 	| NODDCLR 	{ $$.type = INSTOPTION_FLAG; $$.uint_value = NODDCLR; }
2160 	| NODDCHK 	{ $$.type = INSTOPTION_FLAG; $$.uint_value = NODDCHK; }
2161 	| MASK_DISABLE 	{ $$.type = INSTOPTION_FLAG; $$.uint_value = MASK_DISABLE; }
2162 	| EOT 	        { $$.type = INSTOPTION_FLAG; $$.uint_value = EOT; }
2163 	| SWITCH 	{ $$.type = INSTOPTION_FLAG; $$.uint_value = SWITCH; }
2164 	| ATOMIC 	{ $$.type = INSTOPTION_FLAG; $$.uint_value = ATOMIC; }
2165 	| BRANCH_CTRL 	{ $$.type = INSTOPTION_FLAG; $$.uint_value = BRANCH_CTRL; }
2166 	| CMPTCTRL 	{ $$.type = INSTOPTION_FLAG; $$.uint_value = CMPTCTRL; }
2167 	| WECTRL 	{ $$.type = INSTOPTION_FLAG; $$.uint_value = WECTRL; }
2168 	| QTR_2Q 	{ $$.type = INSTOPTION_CHAN_OFFSET; $$.uint_value = 8; }
2169 	| QTR_3Q 	{ $$.type = INSTOPTION_CHAN_OFFSET; $$.uint_value = 16; }
2170 	| QTR_4Q 	{ $$.type = INSTOPTION_CHAN_OFFSET; $$.uint_value = 24; }
2171 	| QTR_2H 	{ $$.type = INSTOPTION_CHAN_OFFSET; $$.uint_value = 16; }
2172 	| QTR_2N
2173         {
2174 		if (p->devinfo->ver >= 20)
2175 			error(&@1, "Channel offset must be multiple of 8 in Xe2+\n");
2176 		$$.type = INSTOPTION_CHAN_OFFSET;
2177 		$$.uint_value = 4;
2178 	}
2179 	| QTR_3N 	{ $$.type = INSTOPTION_CHAN_OFFSET; $$.uint_value = 8; }
2180 	| QTR_4N
2181 	{
2182 		if (p->devinfo->ver >= 20)
2183 			error(&@1, "Channel offset must be multiple of 8 in Xe2+\n");
2184 		$$.type = INSTOPTION_CHAN_OFFSET; $$.uint_value = 12;
2185 	}
2186 	| QTR_5N 	{ $$.type = INSTOPTION_CHAN_OFFSET; $$.uint_value = 16; }
2187 	| QTR_6N
2188 	{
2189 		if (p->devinfo->ver >= 20)
2190 			error(&@1, "Channel offset must be multiple of 8 in Xe2+\n");
2191 		$$.type = INSTOPTION_CHAN_OFFSET; $$.uint_value = 20;
2192 	}
2193 	| QTR_7N 	{ $$.type = INSTOPTION_CHAN_OFFSET; $$.uint_value = 24; }
2194 	| QTR_8N
2195 	{
2196 		if (p->devinfo->ver >= 20)
2197 			error(&@1, "Channel offset must be multiple of 8 in Xe2+\n");
2198 		$$.type = INSTOPTION_CHAN_OFFSET; $$.uint_value = 28;
2199 	}
2200 	| depinfo	{ $$.type = INSTOPTION_DEP_INFO; $$.depinfo_value = $1; }
2201 	;
2202 
2203 %%
2204 
2205 extern int yylineno;
2206 
2207 #ifdef YYBYACC
2208 void
yyerror(YYLTYPE * ltype,char * msg)2209 yyerror(YYLTYPE *ltype, char *msg)
2210 #else
2211 void
2212 yyerror(char *msg)
2213 #endif
2214 {
2215 	fprintf(stderr, "%s: %d: %s at \"%s\"\n",
2216 	        input_filename, yylineno, msg, lex_text());
2217 	++errors;
2218 }
2219