get_lazyops() -> lazyops (#2884)

* get_lazyops() -> lazyops

* don't compare empty mem
This commit is contained in:
George Hotz
2023-12-20 18:04:49 -08:00
committed by GitHub
parent 64dded27f0
commit 7da2325dc7
7 changed files with 14 additions and 12 deletions
+2 -1
View File
@@ -329,9 +329,10 @@ jobs:
- name: Install Python Dependencies
run: pip install -e '.[testing]' --extra-index-url https://download.pytorch.org/whl/cpu
- name: Test HIP compilation on RDNA3 [gfx1100]
# test/test_symbolic_ops.py can't run here, it was comparing empty memory
run: |
export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:/opt/rocm/hip/lib
MOCKHIP=1 HIP=1 python -m pytest -s test/test_hip_rdna3.py test/test_symbolic_ops.py
MOCKHIP=1 HIP=1 python -m pytest -s test/test_hip_rdna3.py
tests:
+1 -1
View File
@@ -43,7 +43,7 @@ if __name__ == "__main__":
out = x.sequential([c1,c2,c3,c4,c5])
schedule = out.lazydata.schedule()
schedule, schedule_input = partition(schedule, lambda x: x.ast.op not in LoadOps and any(y.op in ReduceOps for y in x.ast.get_lazyops()))
schedule, schedule_input = partition(schedule, lambda x: x.ast.op not in LoadOps and any(y.op in ReduceOps for y in x.ast.lazyops))
run_schedule(schedule_input)
run_schedule(schedule[:getenv("CONV")])
print("*** init done ***")
+1 -1
View File
@@ -64,7 +64,7 @@ def universal_test_unary(a, dtype, op):
if dtype in dtypes_float: np.testing.assert_allclose(tensor_value, numpy_value, atol=5 if Device.DEFAULT == "METAL" and op[0] == Tensor.sin else 1e-3, rtol=2 if Device.DEFAULT == "METAL" and op[0] == Tensor.sin else 1e-4 if dtype == dtypes.float32 else 1e-2) # exp and log and sin are approximations (in METAL, the default fast-math versions are less precise) # noqa: E501
else: np.testing.assert_equal(tensor_value, numpy_value)
if op[0] != Tensor.reciprocal: # reciprocal is not supported in most backends
op = [x for x in ast.get_lazyops() if x.op in UnaryOps][0]
op = [x for x in ast.lazyops if x.op in UnaryOps][0]
assert get_lazyop_info(op).dtype == dtype
def universal_test_cast(a, in_dtype, dtype):
+1 -1
View File
@@ -22,7 +22,7 @@ class TestWinograd(unittest.TestCase):
for i,s in enumerate(sched):
if s.ast.op in LoadOps: continue
ops = s.ast.get_lazyops()
ops = s.ast.lazyops
with Timing(f"linearize {i} with {len(ops):4d} ops: "):
l = Linearizer(s.ast)
l.hand_coded_optimizations()
+4 -4
View File
@@ -74,16 +74,16 @@ class Kernel:
self.info: FlopCounter = get_lazyop_info(self.ast)
# there's only allowed to be one reduceop
reduceops = [x for x in self.ast.get_lazyops() if x.op in ReduceOps]
reduceops = [x for x in self.ast.lazyops if x.op in ReduceOps]
assert len(dedup(reduceops)) <= 1, "max one reduce op in an ast"
self.reduceop = reduceops[0] if reduceops else None
# create new shapetrackers inside this kernel, we will permute them
self.bufs: List[Union[MemBuffer, ConstBuffer, LocalBuffer]] = dedup([x.arg for x in self.ast.get_lazyops() if x.op in BufferOps])
self.bufs: List[Union[MemBuffer, ConstBuffer, LocalBuffer]] = dedup([x.arg for x in self.ast.lazyops if x.op in BufferOps])
assert isinstance(self.bufs[0], MemBuffer) and self.bufs[0].idx == 0, f"buffer 0 is not the store buffer {self.bufs[0]}"
# get earlybufs, before the one reduce op
self.earlybufs = [x.arg for x in self.reduceop.get_lazyops() if x.op in BufferOps] if self.reduceop else []
self.earlybufs = [x.arg for x in self.reduceop.lazyops if x.op in BufferOps] if self.reduceop else []
self.full_buf_index: int = self.bufs.index(self.earlybufs[0]) if self.earlybufs else 0
# create the (permuted) shapetrackers
@@ -452,7 +452,7 @@ class Kernel:
self.dont_use_locals = True
elif opt.op == OptOps.PADTO:
assert not vars_from_ast(self.ast), "does not work with symbolic shape"
assert all(op.op is not ReduceOps.MAX for op in self.ast.get_lazyops()), "cannot pad with MAX"
assert all(op.op is not ReduceOps.MAX for op in self.ast.lazyops), "cannot pad with MAX"
padded = False
for i,st in enumerate(self.sts):
if self.sts[i].shape[axis] != 1:
+4 -3
View File
@@ -2,7 +2,7 @@ from __future__ import annotations
from typing import TYPE_CHECKING, Union, Type, Tuple, Any, List, Dict, Callable
import functools
from enum import Enum, auto
from tinygrad.helpers import prod, DType, least_upper_dtype
from tinygrad.helpers import prod, DType, least_upper_dtype, dedup
from tinygrad.shape.symbolic import Variable
from dataclasses import dataclass
@@ -54,10 +54,11 @@ class LazyOp:
@functools.cached_property
def hash(self): return hash((self.op, self.src, self.arg))
def __hash__(self): return self.hash
def get_lazyops(self) -> List[LazyOp]: return [self] + [item for x in self.src for item in x.get_lazyops()]
@functools.cached_property
def lazyops(self) -> List[LazyOp]: return dedup([self] + [item for x in self.src for item in x.lazyops])
def vars_from_ast(ast:LazyOp) -> List[Variable]:
return sorted(set.union(*[x.arg.st.vars() for x in ast.get_lazyops() if x.op in BufferOps], set()), key=lambda x: str(x.expr))
return sorted(set.union(*[x.arg.st.vars() for x in ast.lazyops if x.op in BufferOps], set()), key=lambda x: str(x.expr))
# **************** independent FlopCounter ****************
+1 -1
View File
@@ -31,7 +31,7 @@ def run_schedule(schedule:List[ScheduleItem]):
if si.out.output_buffer is not None:
for i,a in enumerate(si.inputs):
if a.realized == si.out.output_buffer:
if any(not x.arg.st.contiguous for x in si.ast.get_lazyops() if x.op == BufferOps.LOAD and x.arg.idx == i+1):
if any(not x.arg.st.contiguous for x in si.ast.lazyops if x.op == BufferOps.LOAD and x.arg.idx == i+1):
si.out.output_buffer = None
break