static void nv50_blitctx_prepare_state(struct nv50_blitctx *blit) { struct nouveau_channel *chan = blit->screen->base.channel; /* blend state */ BEGIN_RING(chan, RING_3D(COLOR_MASK(0)), 1); OUT_RING (chan, blit->color_mask); BEGIN_RING(chan, RING_3D(BLEND_ENABLE(0)), 1); OUT_RING (chan, 0); BEGIN_RING(chan, RING_3D(LOGIC_OP_ENABLE), 1); OUT_RING (chan, 0); /* rasterizer state */ #ifndef NV50_SCISSORS_CLIPPING BEGIN_RING(chan, RING_3D(SCISSOR_ENABLE(0)), 1); OUT_RING (chan, 1); #endif BEGIN_RING(chan, RING_3D(VERTEX_TWO_SIDE_ENABLE), 1); OUT_RING (chan, 0); BEGIN_RING(chan, RING_3D(FRAG_COLOR_CLAMP_EN), 1); OUT_RING (chan, 0); BEGIN_RING(chan, RING_3D(MULTISAMPLE_ENABLE), 1); OUT_RING (chan, 0); BEGIN_RING(chan, RING_3D(MSAA_MASK(0)), 4); OUT_RING (chan, 0xffff); OUT_RING (chan, 0xffff); OUT_RING (chan, 0xffff); OUT_RING (chan, 0xffff); BEGIN_RING(chan, RING_3D(POLYGON_MODE_FRONT), 3); OUT_RING (chan, NV50_3D_POLYGON_MODE_FRONT_FILL); OUT_RING (chan, NV50_3D_POLYGON_MODE_BACK_FILL); OUT_RING (chan, 0); BEGIN_RING(chan, RING_3D(CULL_FACE_ENABLE), 1); OUT_RING (chan, 0); BEGIN_RING(chan, RING_3D(POLYGON_STIPPLE_ENABLE), 1); OUT_RING (chan, 0); BEGIN_RING(chan, RING_3D(POLYGON_OFFSET_FILL_ENABLE), 1); OUT_RING (chan, 0); /* zsa state */ BEGIN_RING(chan, RING_3D(DEPTH_TEST_ENABLE), 1); OUT_RING (chan, 0); BEGIN_RING(chan, RING_3D(STENCIL_ENABLE), 1); OUT_RING (chan, 0); BEGIN_RING(chan, RING_3D(ALPHA_TEST_ENABLE), 1); OUT_RING (chan, 0); }
/* NOTE: ignoring line_last_pixel */ static void * nv50_rasterizer_state_create(struct pipe_context *pipe, const struct pipe_rasterizer_state *cso) { struct nv50_rasterizer_stateobj *so; uint32_t reg; so = CALLOC_STRUCT(nv50_rasterizer_stateobj); if (!so) return NULL; so->pipe = *cso; #ifndef NV50_SCISSORS_CLIPPING for (int i = 0; i < NV50_MAX_VIEWPORTS; i++) { SB_BEGIN_3D(so, SCISSOR_ENABLE(i), 1); SB_DATA (so, cso->scissor); } #endif SB_BEGIN_3D(so, SHADE_MODEL, 1); SB_DATA (so, cso->flatshade ? NV50_3D_SHADE_MODEL_FLAT : NV50_3D_SHADE_MODEL_SMOOTH); SB_BEGIN_3D(so, PROVOKING_VERTEX_LAST, 1); SB_DATA (so, !cso->flatshade_first); SB_BEGIN_3D(so, VERTEX_TWO_SIDE_ENABLE, 1); SB_DATA (so, cso->light_twoside); SB_BEGIN_3D(so, FRAG_COLOR_CLAMP_EN, 1); SB_DATA (so, cso->clamp_fragment_color ? 0x11111111 : 0x00000000); SB_BEGIN_3D(so, MULTISAMPLE_ENABLE, 1); SB_DATA (so, cso->multisample); SB_BEGIN_3D(so, LINE_WIDTH, 1); SB_DATA (so, fui(cso->line_width)); SB_BEGIN_3D(so, LINE_SMOOTH_ENABLE, 1); SB_DATA (so, cso->line_smooth); SB_BEGIN_3D(so, LINE_STIPPLE_ENABLE, 1); if (cso->line_stipple_enable) { SB_DATA (so, 1); SB_BEGIN_3D(so, LINE_STIPPLE, 1); SB_DATA (so, (cso->line_stipple_pattern << 8) | cso->line_stipple_factor); } else { SB_DATA (so, 0); } if (!cso->point_size_per_vertex) { SB_BEGIN_3D(so, POINT_SIZE, 1); SB_DATA (so, fui(cso->point_size)); } SB_BEGIN_3D(so, POINT_SPRITE_ENABLE, 1); SB_DATA (so, cso->point_quad_rasterization); SB_BEGIN_3D(so, POINT_SMOOTH_ENABLE, 1); SB_DATA (so, cso->point_smooth); SB_BEGIN_3D(so, POLYGON_MODE_FRONT, 3); SB_DATA (so, nvgl_polygon_mode(cso->fill_front)); SB_DATA (so, nvgl_polygon_mode(cso->fill_back)); SB_DATA (so, cso->poly_smooth); SB_BEGIN_3D(so, CULL_FACE_ENABLE, 3); SB_DATA (so, cso->cull_face != PIPE_FACE_NONE); SB_DATA (so, cso->front_ccw ? NV50_3D_FRONT_FACE_CCW : NV50_3D_FRONT_FACE_CW); switch (cso->cull_face) { case PIPE_FACE_FRONT_AND_BACK: SB_DATA(so, NV50_3D_CULL_FACE_FRONT_AND_BACK); break; case PIPE_FACE_FRONT: SB_DATA(so, NV50_3D_CULL_FACE_FRONT); break; case PIPE_FACE_BACK: default: SB_DATA(so, NV50_3D_CULL_FACE_BACK); break; } SB_BEGIN_3D(so, POLYGON_STIPPLE_ENABLE, 1); SB_DATA (so, cso->poly_stipple_enable); SB_BEGIN_3D(so, POLYGON_OFFSET_POINT_ENABLE, 3); SB_DATA (so, cso->offset_point); SB_DATA (so, cso->offset_line); SB_DATA (so, cso->offset_tri); if (cso->offset_point || cso->offset_line || cso->offset_tri) { SB_BEGIN_3D(so, POLYGON_OFFSET_FACTOR, 1); SB_DATA (so, fui(cso->offset_scale)); SB_BEGIN_3D(so, POLYGON_OFFSET_UNITS, 1); SB_DATA (so, fui(cso->offset_units * 2.0f)); SB_BEGIN_3D(so, POLYGON_OFFSET_CLAMP, 1); SB_DATA (so, fui(cso->offset_clamp)); } if (cso->depth_clip) { reg = 0; } else { reg = NV50_3D_VIEW_VOLUME_CLIP_CTRL_DEPTH_CLAMP_NEAR | NV50_3D_VIEW_VOLUME_CLIP_CTRL_DEPTH_CLAMP_FAR | NV50_3D_VIEW_VOLUME_CLIP_CTRL_UNK12_UNK1; } #ifndef NV50_SCISSORS_CLIPPING reg |= NV50_3D_VIEW_VOLUME_CLIP_CTRL_UNK7 | NV50_3D_VIEW_VOLUME_CLIP_CTRL_UNK12_UNK1; #endif SB_BEGIN_3D(so, VIEW_VOLUME_CLIP_CTRL, 1); SB_DATA (so, reg); SB_BEGIN_3D(so, DEPTH_CLIP_NEGATIVE_Z, 1); SB_DATA (so, cso->clip_halfz); SB_BEGIN_3D(so, PIXEL_CENTER_INTEGER, 1); SB_DATA (so, !cso->half_pixel_center); assert(so->size <= (sizeof(so->state) / sizeof(so->state[0]))); return (void *)so; }
static void nv50_screen_init_hwctx(struct nv50_screen *screen) { struct nouveau_pushbuf *push = screen->base.pushbuf; struct nv04_fifo *fifo; unsigned i; fifo = (struct nv04_fifo *)screen->base.channel->data; BEGIN_NV04(push, SUBC_M2MF(NV01_SUBCHAN_OBJECT), 1); PUSH_DATA (push, screen->m2mf->handle); BEGIN_NV04(push, SUBC_M2MF(NV03_M2MF_DMA_NOTIFY), 3); PUSH_DATA (push, screen->sync->handle); PUSH_DATA (push, fifo->vram); PUSH_DATA (push, fifo->vram); BEGIN_NV04(push, SUBC_2D(NV01_SUBCHAN_OBJECT), 1); PUSH_DATA (push, screen->eng2d->handle); BEGIN_NV04(push, NV50_2D(DMA_NOTIFY), 4); PUSH_DATA (push, screen->sync->handle); PUSH_DATA (push, fifo->vram); PUSH_DATA (push, fifo->vram); PUSH_DATA (push, fifo->vram); BEGIN_NV04(push, NV50_2D(OPERATION), 1); PUSH_DATA (push, NV50_2D_OPERATION_SRCCOPY); BEGIN_NV04(push, NV50_2D(CLIP_ENABLE), 1); PUSH_DATA (push, 0); BEGIN_NV04(push, NV50_2D(COLOR_KEY_ENABLE), 1); PUSH_DATA (push, 0); BEGIN_NV04(push, SUBC_2D(0x0888), 1); PUSH_DATA (push, 1); BEGIN_NV04(push, SUBC_3D(NV01_SUBCHAN_OBJECT), 1); PUSH_DATA (push, screen->tesla->handle); BEGIN_NV04(push, NV50_3D(COND_MODE), 1); PUSH_DATA (push, NV50_3D_COND_MODE_ALWAYS); BEGIN_NV04(push, NV50_3D(DMA_NOTIFY), 1); PUSH_DATA (push, screen->sync->handle); BEGIN_NV04(push, NV50_3D(DMA_ZETA), 11); for (i = 0; i < 11; ++i) PUSH_DATA(push, fifo->vram); BEGIN_NV04(push, NV50_3D(DMA_COLOR(0)), NV50_3D_DMA_COLOR__LEN); for (i = 0; i < NV50_3D_DMA_COLOR__LEN; ++i) PUSH_DATA(push, fifo->vram); BEGIN_NV04(push, NV50_3D(REG_MODE), 1); PUSH_DATA (push, NV50_3D_REG_MODE_STRIPED); BEGIN_NV04(push, NV50_3D(UNK1400_LANES), 1); PUSH_DATA (push, 0xf); if (debug_get_bool_option("NOUVEAU_SHADER_WATCHDOG", TRUE)) { BEGIN_NV04(push, NV50_3D(WATCHDOG_TIMER), 1); PUSH_DATA (push, 0x18); } BEGIN_NV04(push, NV50_3D(RT_CONTROL), 1); PUSH_DATA (push, 1); BEGIN_NV04(push, NV50_3D(CSAA_ENABLE), 1); PUSH_DATA (push, 0); BEGIN_NV04(push, NV50_3D(MULTISAMPLE_ENABLE), 1); PUSH_DATA (push, 0); BEGIN_NV04(push, NV50_3D(MULTISAMPLE_MODE), 1); PUSH_DATA (push, NV50_3D_MULTISAMPLE_MODE_MS1); BEGIN_NV04(push, NV50_3D(MULTISAMPLE_CTRL), 1); PUSH_DATA (push, 0); BEGIN_NV04(push, NV50_3D(LINE_LAST_PIXEL), 1); PUSH_DATA (push, 0); BEGIN_NV04(push, NV50_3D(BLEND_SEPARATE_ALPHA), 1); PUSH_DATA (push, 1); if (screen->tesla->oclass >= NVA0_3D_CLASS) { BEGIN_NV04(push, SUBC_3D(NVA0_3D_TEX_MISC), 1); PUSH_DATA (push, NVA0_3D_TEX_MISC_SEAMLESS_CUBE_MAP); } BEGIN_NV04(push, NV50_3D(SCREEN_Y_CONTROL), 1); PUSH_DATA (push, 0); BEGIN_NV04(push, NV50_3D(WINDOW_OFFSET_X), 2); PUSH_DATA (push, 0); PUSH_DATA (push, 0); BEGIN_NV04(push, NV50_3D(ZCULL_REGION), 1); PUSH_DATA (push, 0x3f); BEGIN_NV04(push, NV50_3D(VP_ADDRESS_HIGH), 2); PUSH_DATAh(push, screen->code->offset + (0 << NV50_CODE_BO_SIZE_LOG2)); PUSH_DATA (push, screen->code->offset + (0 << NV50_CODE_BO_SIZE_LOG2)); BEGIN_NV04(push, NV50_3D(FP_ADDRESS_HIGH), 2); PUSH_DATAh(push, screen->code->offset + (1 << NV50_CODE_BO_SIZE_LOG2)); PUSH_DATA (push, screen->code->offset + (1 << NV50_CODE_BO_SIZE_LOG2)); BEGIN_NV04(push, NV50_3D(GP_ADDRESS_HIGH), 2); PUSH_DATAh(push, screen->code->offset + (2 << NV50_CODE_BO_SIZE_LOG2)); PUSH_DATA (push, screen->code->offset + (2 << NV50_CODE_BO_SIZE_LOG2)); BEGIN_NV04(push, NV50_3D(LOCAL_ADDRESS_HIGH), 3); PUSH_DATAh(push, screen->tls_bo->offset); PUSH_DATA (push, screen->tls_bo->offset); PUSH_DATA (push, util_logbase2(screen->cur_tls_space / 8)); BEGIN_NV04(push, NV50_3D(STACK_ADDRESS_HIGH), 3); PUSH_DATAh(push, screen->stack_bo->offset); PUSH_DATA (push, screen->stack_bo->offset); PUSH_DATA (push, 4); BEGIN_NV04(push, NV50_3D(CB_DEF_ADDRESS_HIGH), 3); PUSH_DATAh(push, screen->uniforms->offset + (0 << 16)); PUSH_DATA (push, screen->uniforms->offset + (0 << 16)); PUSH_DATA (push, (NV50_CB_PVP << 16) | 0x0000); BEGIN_NV04(push, NV50_3D(CB_DEF_ADDRESS_HIGH), 3); PUSH_DATAh(push, screen->uniforms->offset + (1 << 16)); PUSH_DATA (push, screen->uniforms->offset + (1 << 16)); PUSH_DATA (push, (NV50_CB_PGP << 16) | 0x0000); BEGIN_NV04(push, NV50_3D(CB_DEF_ADDRESS_HIGH), 3); PUSH_DATAh(push, screen->uniforms->offset + (2 << 16)); PUSH_DATA (push, screen->uniforms->offset + (2 << 16)); PUSH_DATA (push, (NV50_CB_PFP << 16) | 0x0000); BEGIN_NV04(push, NV50_3D(CB_DEF_ADDRESS_HIGH), 3); PUSH_DATAh(push, screen->uniforms->offset + (3 << 16)); PUSH_DATA (push, screen->uniforms->offset + (3 << 16)); PUSH_DATA (push, (NV50_CB_AUX << 16) | 0x0200); BEGIN_NI04(push, NV50_3D(SET_PROGRAM_CB), 3); PUSH_DATA (push, (NV50_CB_AUX << 12) | 0xf01); PUSH_DATA (push, (NV50_CB_AUX << 12) | 0xf21); PUSH_DATA (push, (NV50_CB_AUX << 12) | 0xf31); /* return { 0.0, 0.0, 0.0, 0.0 } on out-of-bounds vtxbuf access */ BEGIN_NV04(push, NV50_3D(CB_ADDR), 1); PUSH_DATA (push, ((1 << 9) << 6) | NV50_CB_AUX); BEGIN_NI04(push, NV50_3D(CB_DATA(0)), 4); PUSH_DATAf(push, 0.0f); PUSH_DATAf(push, 0.0f); PUSH_DATAf(push, 0.0f); PUSH_DATAf(push, 0.0f); BEGIN_NV04(push, NV50_3D(VERTEX_RUNOUT_ADDRESS_HIGH), 2); PUSH_DATAh(push, screen->uniforms->offset + (3 << 16) + (1 << 9)); PUSH_DATA (push, screen->uniforms->offset + (3 << 16) + (1 << 9)); /* max TIC (bits 4:8) & TSC bindings, per program type */ for (i = 0; i < 3; ++i) { BEGIN_NV04(push, NV50_3D(TEX_LIMITS(i)), 1); PUSH_DATA (push, 0x54); } BEGIN_NV04(push, NV50_3D(TIC_ADDRESS_HIGH), 3); PUSH_DATAh(push, screen->txc->offset); PUSH_DATA (push, screen->txc->offset); PUSH_DATA (push, NV50_TIC_MAX_ENTRIES - 1); BEGIN_NV04(push, NV50_3D(TSC_ADDRESS_HIGH), 3); PUSH_DATAh(push, screen->txc->offset + 65536); PUSH_DATA (push, screen->txc->offset + 65536); PUSH_DATA (push, NV50_TSC_MAX_ENTRIES - 1); BEGIN_NV04(push, NV50_3D(LINKED_TSC), 1); PUSH_DATA (push, 0); BEGIN_NV04(push, NV50_3D(CLIP_RECTS_EN), 1); PUSH_DATA (push, 0); BEGIN_NV04(push, NV50_3D(CLIP_RECTS_MODE), 1); PUSH_DATA (push, NV50_3D_CLIP_RECTS_MODE_INSIDE_ANY); BEGIN_NV04(push, NV50_3D(CLIP_RECT_HORIZ(0)), 8 * 2); for (i = 0; i < 8 * 2; ++i) PUSH_DATA(push, 0); BEGIN_NV04(push, NV50_3D(CLIPID_ENABLE), 1); PUSH_DATA (push, 0); BEGIN_NV04(push, NV50_3D(VIEWPORT_TRANSFORM_EN), 1); PUSH_DATA (push, 1); BEGIN_NV04(push, NV50_3D(DEPTH_RANGE_NEAR(0)), 2); PUSH_DATAf(push, 0.0f); PUSH_DATAf(push, 1.0f); BEGIN_NV04(push, NV50_3D(VIEW_VOLUME_CLIP_CTRL), 1); #ifdef NV50_SCISSORS_CLIPPING PUSH_DATA (push, 0x0000); #else PUSH_DATA (push, 0x1080); #endif BEGIN_NV04(push, NV50_3D(CLEAR_FLAGS), 1); PUSH_DATA (push, NV50_3D_CLEAR_FLAGS_CLEAR_RECT_VIEWPORT); /* We use scissors instead of exact view volume clipping, * so they're always enabled. */ BEGIN_NV04(push, NV50_3D(SCISSOR_ENABLE(0)), 3); PUSH_DATA (push, 1); PUSH_DATA (push, 8192 << 16); PUSH_DATA (push, 8192 << 16); BEGIN_NV04(push, NV50_3D(RASTERIZE_ENABLE), 1); PUSH_DATA (push, 1); BEGIN_NV04(push, NV50_3D(POINT_RASTER_RULES), 1); PUSH_DATA (push, NV50_3D_POINT_RASTER_RULES_OGL); BEGIN_NV04(push, NV50_3D(FRAG_COLOR_CLAMP_EN), 1); PUSH_DATA (push, 0x11111111); BEGIN_NV04(push, NV50_3D(EDGEFLAG), 1); PUSH_DATA (push, 1); PUSH_KICK (push); }