58,6 → 58,7 |
} atom_exec_context; |
|
int atom_debug = 0; |
static void atom_execute_table_locked(struct atom_context *ctx, int index, uint32_t * params); |
void atom_execute_table(struct atom_context *ctx, int index, uint32_t * params); |
|
static uint32_t atom_arg_mask[8] = |
245,6 → 246,9 |
case ATOM_WS_ATTRIBUTES: |
val = gctx->io_attr; |
break; |
case ATOM_WS_REGPTR: |
val = gctx->reg_block; |
break; |
default: |
val = ctx->ws[idx]; |
} |
384,6 → 388,32 |
return atom_get_src_int(ctx, attr, ptr, NULL, 1); |
} |
|
static uint32_t atom_get_src_direct(atom_exec_context *ctx, uint8_t align, int *ptr) |
{ |
uint32_t val = 0xCDCDCDCD; |
|
switch (align) { |
case ATOM_SRC_DWORD: |
val = U32(*ptr); |
(*ptr) += 4; |
break; |
case ATOM_SRC_WORD0: |
case ATOM_SRC_WORD8: |
case ATOM_SRC_WORD16: |
val = U16(*ptr); |
(*ptr) += 2; |
break; |
case ATOM_SRC_BYTE0: |
case ATOM_SRC_BYTE8: |
case ATOM_SRC_BYTE16: |
case ATOM_SRC_BYTE24: |
val = U8(*ptr); |
(*ptr)++; |
break; |
} |
return val; |
} |
|
static uint32_t atom_get_dst(atom_exec_context *ctx, int arg, uint8_t attr, |
int *ptr, uint32_t *saved, int print) |
{ |
481,6 → 511,9 |
case ATOM_WS_ATTRIBUTES: |
gctx->io_attr = val; |
break; |
case ATOM_WS_REGPTR: |
gctx->reg_block = val; |
break; |
default: |
ctx->ws[idx] = val; |
} |
573,7 → 606,7 |
else |
SDEBUG(" table: %d\n", idx); |
if (U16(ctx->ctx->cmd_table + 4 + 2 * idx)) |
atom_execute_table(ctx->ctx, idx, ctx->ps + ctx->ps_shift); |
atom_execute_table_locked(ctx->ctx, idx, ctx->ps + ctx->ps_shift); |
} |
|
static void atom_op_clear(atom_exec_context *ctx, int *ptr, int arg) |
676,7 → 709,7 |
SDEBUG(" dst: "); |
dst = atom_get_dst(ctx, arg, attr, ptr, &saved, 1); |
SDEBUG(" src1: "); |
src1 = atom_get_src(ctx, attr, ptr); |
src1 = atom_get_src_direct(ctx, ((attr >> 3) & 7), ptr); |
SDEBUG(" src2: "); |
src2 = atom_get_src(ctx, attr, ptr); |
dst &= src1; |
808,6 → 841,38 |
SDEBUG(" base: 0x%04X\n", ctx->ctx->reg_block); |
} |
|
static void atom_op_shift_left(atom_exec_context *ctx, int *ptr, int arg) |
{ |
uint8_t attr = U8((*ptr)++), shift; |
uint32_t saved, dst; |
int dptr = *ptr; |
attr &= 0x38; |
attr |= atom_def_dst[attr >> 3] << 6; |
SDEBUG(" dst: "); |
dst = atom_get_dst(ctx, arg, attr, ptr, &saved, 1); |
shift = atom_get_src_direct(ctx, ATOM_SRC_BYTE0, ptr); |
SDEBUG(" shift: %d\n", shift); |
dst <<= shift; |
SDEBUG(" dst: "); |
atom_put_dst(ctx, arg, attr, &dptr, dst, saved); |
} |
|
static void atom_op_shift_right(atom_exec_context *ctx, int *ptr, int arg) |
{ |
uint8_t attr = U8((*ptr)++), shift; |
uint32_t saved, dst; |
int dptr = *ptr; |
attr &= 0x38; |
attr |= atom_def_dst[attr >> 3] << 6; |
SDEBUG(" dst: "); |
dst = atom_get_dst(ctx, arg, attr, ptr, &saved, 1); |
shift = atom_get_src_direct(ctx, ATOM_SRC_BYTE0, ptr); |
SDEBUG(" shift: %d\n", shift); |
dst >>= shift; |
SDEBUG(" dst: "); |
atom_put_dst(ctx, arg, attr, &dptr, dst, saved); |
} |
|
static void atom_op_shl(atom_exec_context *ctx, int *ptr, int arg) |
{ |
uint8_t attr = U8((*ptr)++), shift; |
817,7 → 882,7 |
attr |= atom_def_dst[attr >> 3] << 6; |
SDEBUG(" dst: "); |
dst = atom_get_dst(ctx, arg, attr, ptr, &saved, 1); |
shift = U8((*ptr)++); |
shift = atom_get_src(ctx, attr, ptr); |
SDEBUG(" shift: %d\n", shift); |
dst <<= shift; |
SDEBUG(" dst: "); |
833,7 → 898,7 |
attr |= atom_def_dst[attr >> 3] << 6; |
SDEBUG(" dst: "); |
dst = atom_get_dst(ctx, arg, attr, ptr, &saved, 1); |
shift = U8((*ptr)++); |
shift = atom_get_src(ctx, attr, ptr); |
SDEBUG(" shift: %d\n", shift); |
dst >>= shift; |
SDEBUG(" dst: "); |
936,18 → 1001,18 |
atom_op_or, ATOM_ARG_FB}, { |
atom_op_or, ATOM_ARG_PLL}, { |
atom_op_or, ATOM_ARG_MC}, { |
atom_op_shl, ATOM_ARG_REG}, { |
atom_op_shl, ATOM_ARG_PS}, { |
atom_op_shl, ATOM_ARG_WS}, { |
atom_op_shl, ATOM_ARG_FB}, { |
atom_op_shl, ATOM_ARG_PLL}, { |
atom_op_shl, ATOM_ARG_MC}, { |
atom_op_shr, ATOM_ARG_REG}, { |
atom_op_shr, ATOM_ARG_PS}, { |
atom_op_shr, ATOM_ARG_WS}, { |
atom_op_shr, ATOM_ARG_FB}, { |
atom_op_shr, ATOM_ARG_PLL}, { |
atom_op_shr, ATOM_ARG_MC}, { |
atom_op_shift_left, ATOM_ARG_REG}, { |
atom_op_shift_left, ATOM_ARG_PS}, { |
atom_op_shift_left, ATOM_ARG_WS}, { |
atom_op_shift_left, ATOM_ARG_FB}, { |
atom_op_shift_left, ATOM_ARG_PLL}, { |
atom_op_shift_left, ATOM_ARG_MC}, { |
atom_op_shift_right, ATOM_ARG_REG}, { |
atom_op_shift_right, ATOM_ARG_PS}, { |
atom_op_shift_right, ATOM_ARG_WS}, { |
atom_op_shift_right, ATOM_ARG_FB}, { |
atom_op_shift_right, ATOM_ARG_PLL}, { |
atom_op_shift_right, ATOM_ARG_MC}, { |
atom_op_mul, ATOM_ARG_REG}, { |
atom_op_mul, ATOM_ARG_PS}, { |
atom_op_mul, ATOM_ARG_WS}, { |
1040,7 → 1105,7 |
atom_op_shr, ATOM_ARG_MC}, { |
atom_op_debug, 0},}; |
|
void atom_execute_table(struct atom_context *ctx, int index, uint32_t * params) |
static void atom_execute_table_locked(struct atom_context *ctx, int index, uint32_t * params) |
{ |
int base = CU16(ctx->cmd_table + 4 + 2 * index); |
int len, ws, ps, ptr; |
1057,8 → 1122,6 |
|
SDEBUG(">> execute %04X (len %d, WS %d, PS %d)\n", base, len, ws, ps); |
|
/* reset reg block */ |
ctx->reg_block = 0; |
ectx.ctx = ctx; |
ectx.ps_shift = ps / 4; |
ectx.start = base; |
1092,6 → 1155,19 |
kfree(ectx.ws); |
} |
|
void atom_execute_table(struct atom_context *ctx, int index, uint32_t * params) |
{ |
mutex_lock(&ctx->mutex); |
/* reset reg block */ |
ctx->reg_block = 0; |
/* reset fb window */ |
ctx->fb_base = 0; |
/* reset io mode */ |
ctx->io_mode = ATOM_IO_MM; |
atom_execute_table_locked(ctx, index, params); |
mutex_unlock(&ctx->mutex); |
} |
|
static int atom_iio_len[] = { 1, 2, 3, 3, 3, 3, 4, 4, 4, 3 }; |
|
static void atom_index_iio(struct atom_context *ctx, int base) |