[Mesa-dev] [PATCH 20/21] [RFC] r600/sb: make it work?
Dave Airlie
airlied at gmail.com
Wed Jan 10 06:48:59 UTC 2018
From: Dave Airlie <airlied at redhat.com>
This has some hacks in it that in the end make heaven run
---
src/gallium/drivers/r600/sb/sb_bc_builder.cpp | 2 +-
src/gallium/drivers/r600/sb/sb_bc_decoder.cpp | 1 +
src/gallium/drivers/r600/sb/sb_bc_finalize.cpp | 10 +++++++-
src/gallium/drivers/r600/sb/sb_gcm.cpp | 32 +++++++++++++++++---------
src/gallium/drivers/r600/sb/sb_gvn.cpp | 3 +++
src/gallium/drivers/r600/sb/sb_liveness.cpp | 4 ++++
src/gallium/drivers/r600/sb/sb_pass.h | 6 ++---
src/gallium/drivers/r600/sb/sb_ra_checker.cpp | 5 +++-
src/gallium/drivers/r600/sb/sb_sched.cpp | 4 ++--
src/gallium/drivers/r600/sb/sb_ssa_builder.cpp | 4 +++-
src/gallium/drivers/r600/sb/sb_valtable.cpp | 2 +-
11 files changed, 52 insertions(+), 21 deletions(-)
diff --git a/src/gallium/drivers/r600/sb/sb_bc_builder.cpp b/src/gallium/drivers/r600/sb/sb_bc_builder.cpp
index ea91e197c0..40d950e857 100644
--- a/src/gallium/drivers/r600/sb/sb_bc_builder.cpp
+++ b/src/gallium/drivers/r600/sb/sb_bc_builder.cpp
@@ -398,7 +398,7 @@ int bc_builder::build_alu(alu_node* n) {
.LDS_OP((bc.op_ptr->opcode[1] >> 8) & 0xff)
.IDX_OFFSET_0((bc.lds_idx_offset >> 0) & 1)
.IDX_OFFSET_2((bc.lds_idx_offset >> 2) & 1)
- .DST_CHAN(bc.dst_chan)
+ .DST_CHAN(0)
.IDX_OFFSET_3((bc.lds_idx_offset >> 3) & 1);
return 0;
diff --git a/src/gallium/drivers/r600/sb/sb_bc_decoder.cpp b/src/gallium/drivers/r600/sb/sb_bc_decoder.cpp
index 1fa580e66d..823b927881 100644
--- a/src/gallium/drivers/r600/sb/sb_bc_decoder.cpp
+++ b/src/gallium/drivers/r600/sb/sb_bc_decoder.cpp
@@ -329,6 +329,7 @@ int bc_decoder::decode_alu(unsigned & i, bc_alu& bc) {
bc.src[2].sel = iw1.get_SRC2_SEL();
bc.src[2].rel = iw1.get_SRC2_REL();
bc.dst_chan = iw1.get_DST_CHAN();
+ bc.dst_gpr = 0;
// TODO: clean up
for (size_t k = 0, e = r600_alu_op_table_size(); k != e; k++) {
if (((r600_alu_op_table[k].opcode[1] >> 8) & 0xff) == iw1.get_LDS_OP()) {
diff --git a/src/gallium/drivers/r600/sb/sb_bc_finalize.cpp b/src/gallium/drivers/r600/sb/sb_bc_finalize.cpp
index 099b295f18..5b202c3737 100644
--- a/src/gallium/drivers/r600/sb/sb_bc_finalize.cpp
+++ b/src/gallium/drivers/r600/sb/sb_bc_finalize.cpp
@@ -293,6 +293,10 @@ void bc_finalizer::finalize_alu_group(alu_group_node* g, node *prev_node) {
unsigned slot = n->bc.slot;
value *d = n->dst.empty() ? NULL : n->dst[0];
+ if (n->bc.op == LDS_OP1_LDS_READ_RET && !d) {
+ n->remove();
+ continue;
+ }
if (d && d->is_special_reg()) {
assert((n->bc.op_ptr->flags & AF_MOVA) || d->is_geometry_emit() || d->is_lds_oq() || d->is_lds_access());
d = NULL;
@@ -339,7 +343,8 @@ void bc_finalizer::finalize_alu_group(alu_group_node* g, node *prev_node) {
insert_rv6xx_load_ar_workaround(g);
}
}
- last->bc.last = 1;
+ if (last)
+ last->bc.last = 1;
}
bool bc_finalizer::finalize_alu_src(alu_group_node* g, alu_node* a, alu_group_node *prev) {
@@ -358,6 +363,9 @@ bool bc_finalizer::finalize_alu_src(alu_group_node* g, alu_node* a, alu_group_no
assert(v);
bc_alu_src &src = a->bc.src[si];
+
+ if (si >= 3)
+ continue;
sel_chan sc;
src.rel = 0;
diff --git a/src/gallium/drivers/r600/sb/sb_gcm.cpp b/src/gallium/drivers/r600/sb/sb_gcm.cpp
index 7776a10fc8..c08648ba4a 100644
--- a/src/gallium/drivers/r600/sb/sb_gcm.cpp
+++ b/src/gallium/drivers/r600/sb/sb_gcm.cpp
@@ -158,18 +158,19 @@ void gcm::sched_early(container_node *n) {
}
}
-void gcm::td_schedule(bb_node *bb, node *n) {
+bool gcm::td_schedule(bb_node *bb, node *n) {
+ bool pushed_front = false;
GCM_DUMP(
sblog << "scheduling : ";
dump::dump_op(n);
sblog << "\n";
);
- td_release_uses(n->dst);
+ pushed_front = td_release_uses(n->dst);
bb->push_back(n);
op_map[n].top_bb = bb;
-
+ return pushed_front;
}
void gcm::td_sched_bb(bb_node* bb) {
@@ -181,8 +182,10 @@ void gcm::td_sched_bb(bb_node* bb) {
for (sq_iterator N, I = ready.begin(), E = ready.end(); I != E;
I = N) {
N = I; ++N;
- td_schedule(bb, *I);
+ bool pushed_front = td_schedule(bb, *I);
ready.erase(I);
+ if (pushed_front)
+ break;
}
}
}
@@ -191,7 +194,7 @@ bool gcm::td_is_ready(node* n) {
return uses[n] == 0;
}
-void gcm::td_release_val(value *v) {
+bool gcm::td_release_val(value *v) {
GCM_DUMP(
sblog << "td checking uses: ";
@@ -199,6 +202,7 @@ void gcm::td_release_val(value *v) {
sblog << "\n";
);
+ bool pushed_front = false;
for (uselist::iterator I = v->uses.begin(), E = v->uses.end(); I != E; ++I) {
node *op = *I;
if (op->parent != &pending) {
@@ -220,23 +224,29 @@ void gcm::td_release_val(value *v) {
);
pending.remove_node(op);
- ready.push_back(op);
+ if (op->produces_lds_oq() || op->consumes_lds_oq()) {
+ ready.push_front(op);
+ pushed_front = true;
+ } else
+ ready.push_back(op);
}
}
-
+ return pushed_front;
}
-void gcm::td_release_uses(vvec& v) {
+bool gcm::td_release_uses(vvec& v) {
+ bool pushed_front = false;
for (vvec::iterator I = v.begin(), E = v.end(); I != E; ++I) {
value *v = *I;
if (!v)
continue;
if (v->is_rel())
- td_release_uses(v->mdef);
+ pushed_front |= td_release_uses(v->mdef);
else
- td_release_val(v);
+ pushed_front |= td_release_val(v);
}
+ return pushed_front;
}
void gcm::sched_late(container_node *n) {
@@ -637,7 +647,7 @@ void gcm::add_ready(node *n) {
sched_queue_id sq = sh.get_queue_id(n);
if (n->flags & NF_SCHEDULE_EARLY)
bu_ready_early[sq].push_back(n);
- else if (sq == SQ_ALU && n->is_copy_mov())
+ else if (sq == SQ_ALU && (n->is_copy_mov() || n->consumes_lds_oq() || n->produces_lds_oq()))
bu_ready[sq].push_front(n);
else if (n->is_alu_inst()) {
alu_node *a = static_cast<alu_node*>(n);
diff --git a/src/gallium/drivers/r600/sb/sb_gvn.cpp b/src/gallium/drivers/r600/sb/sb_gvn.cpp
index caea4ec666..bf7b915e7a 100644
--- a/src/gallium/drivers/r600/sb/sb_gvn.cpp
+++ b/src/gallium/drivers/r600/sb/sb_gvn.cpp
@@ -133,6 +133,9 @@ bool gvn::visit(region_node& n, bool enter) {
}
bool gvn::process_src(value* &v, bool rewrite) {
+
+ if (v->is_lds_oq() || v->is_lds_access())
+ return false;
if (!v->gvn_source)
sh.vt.add_value(v);
diff --git a/src/gallium/drivers/r600/sb/sb_liveness.cpp b/src/gallium/drivers/r600/sb/sb_liveness.cpp
index 8ecc9a5987..2c52581054 100644
--- a/src/gallium/drivers/r600/sb/sb_liveness.cpp
+++ b/src/gallium/drivers/r600/sb/sb_liveness.cpp
@@ -217,6 +217,10 @@ void liveness::update_interferences() {
}
bool liveness::remove_val(value *v) {
+ if (v->is_lds_access()) {
+ v->flags &= ~VLF_DEAD;
+ return true;
+ }
if (live.remove_val(v)) {
v->flags &= ~VLF_DEAD;
return true;
diff --git a/src/gallium/drivers/r600/sb/sb_pass.h b/src/gallium/drivers/r600/sb/sb_pass.h
index a21b0bf997..b62fbaedf9 100644
--- a/src/gallium/drivers/r600/sb/sb_pass.h
+++ b/src/gallium/drivers/r600/sb/sb_pass.h
@@ -278,9 +278,9 @@ private:
void sched_early(container_node *n);
void td_sched_bb(bb_node *bb);
bool td_is_ready(node *n);
- void td_release_uses(vvec &v);
- void td_release_val(value *v);
- void td_schedule(bb_node *bb, node *n);
+ bool td_release_uses(vvec &v);
+ bool td_release_val(value *v);
+ bool td_schedule(bb_node *bb, node *n);
void sched_late(container_node *n);
void bu_sched_bb(bb_node *bb);
diff --git a/src/gallium/drivers/r600/sb/sb_ra_checker.cpp b/src/gallium/drivers/r600/sb/sb_ra_checker.cpp
index 9681e69f6c..563b92a580 100644
--- a/src/gallium/drivers/r600/sb/sb_ra_checker.cpp
+++ b/src/gallium/drivers/r600/sb/sb_ra_checker.cpp
@@ -214,7 +214,10 @@ void ra_checker::check_alu_group(alu_group_node *g) {
process_op_dst(a);
unsigned slot = a->bc.slot;
- prev_dst[slot] = a->dst[0];
+ if (a->dst.size())
+ prev_dst[slot] = a->dst[0];
+ else
+ prev_dst[slot] = NULL;
}
}
diff --git a/src/gallium/drivers/r600/sb/sb_sched.cpp b/src/gallium/drivers/r600/sb/sb_sched.cpp
index f5fd84d54a..bf8f1308ee 100644
--- a/src/gallium/drivers/r600/sb/sb_sched.cpp
+++ b/src/gallium/drivers/r600/sb/sb_sched.cpp
@@ -1556,7 +1556,7 @@ void post_scheduler::recolor_locals() {
for (unsigned s = 0; s < ctx.num_slots; ++s) {
alu_node *n = rt.slot(s);
- if (n) {
+ if (n && n->dst.size()) {
value *d = n->dst[0];
if (d && d->is_sgpr() && !d->is_prealloc()) {
recolor_local(d);
@@ -1910,7 +1910,7 @@ void post_scheduler::release_op(node *n) {
if (n->is_copy_mov()) {
ready_copies.push_back(n);
- } else if (n->is_mova() || n->is_pred_set()) {
+ } else if (n->is_mova() || n->is_pred_set() || n->consumes_lds_oq() || n->produces_lds_oq()) {
ready.push_front(n);
} else {
ready.push_back(n);
diff --git a/src/gallium/drivers/r600/sb/sb_ssa_builder.cpp b/src/gallium/drivers/r600/sb/sb_ssa_builder.cpp
index 5cd41c2aab..239fad9d84 100644
--- a/src/gallium/drivers/r600/sb/sb_ssa_builder.cpp
+++ b/src/gallium/drivers/r600/sb/sb_ssa_builder.cpp
@@ -53,6 +53,8 @@ void ssa_prepare::add_defs(node &n) {
if (!v)
continue;
+ if (v->is_lds_access() || v->is_lds_oq())
+ continue;
if (v->is_rel()) {
s.add_vec(v->mdef);
} else
@@ -167,7 +169,7 @@ bool ssa_rename::visit(alu_node& n, bool enter) {
node *psi = NULL;
- if (n.pred && n.dst[0]) {
+ if (n.pred && n.dst[0] && !n.dst[0]->is_lds_access() && !n.dst[0]->is_lds_oq()) {
value *d = n.dst[0];
unsigned index = get_index(rename_stack.top(), d);
diff --git a/src/gallium/drivers/r600/sb/sb_valtable.cpp b/src/gallium/drivers/r600/sb/sb_valtable.cpp
index 41cfbf0946..22ef1164c0 100644
--- a/src/gallium/drivers/r600/sb/sb_valtable.cpp
+++ b/src/gallium/drivers/r600/sb/sb_valtable.cpp
@@ -185,7 +185,7 @@ value_hash value::hash() {
return ghash;
if (is_rel())
ghash = rel_hash();
- else if (def)
+ else if (def && !is_dead())
ghash = def->hash();
else
ghash = ((uintptr_t)this) | 1;
--
2.14.3
More information about the mesa-dev
mailing list