Skip to content

Instantly share code, notes, and snippets.

@zygoloid
Created May 24, 2024 20:56
Show Gist options
  • Save zygoloid/16d7b6f528fb0bf440f3c3c745acf6b4 to your computer and use it in GitHub Desktop.
Save zygoloid/16d7b6f528fb0bf440f3c3c745acf6b4 to your computer and use it in GitHub Desktop.
problem with performing rewrites in the generic definition context

Problem

In a generic context, we don't in general know whether the type being subscripted or indexed implements IndirectIndexWith or BindToRef. If we perform a rewrite to the corresponding interfaces in a generic context, the behavior can depend on which interfaces we happen to know the type implements, and the behavior can change sharply if we learn more about the interfaces implemented by the type. This knowledge can even arise implicitly in some cases.

class Slice {}
class Element {}
class Member {}

impl Slice as IndirectIndexWith(i32) where .Result = Element;
impl forall [T:! type] Member as BindToValue(T) where .Result = i32 {
  fn Op[self: Self](x: T) -> i32 {
    return 1;
  }
}
impl forall [T:! type] Member as BindToRef(T) where .Result = i32 {
  fn Op[self: Self](x: T) -> i32 {
    return 2;
  }
}

class Generic(T:! type) {}

fn F[I:! IndexWith(i32)](unused g: Generic(I), i: I) -> i32 {
  return i[0].({} as Member);
}

fn Run() {
  Print("{0}", F({}, {} as Slice));
}

The behavior here depends on whether I is known to implement IndirectIndexWith(i32).

  • If not, then i[0] is a value expression, the binding uses BindToValue, and the program prints 1.
  • If so, then i[0] is a reference expression, the binding uses BindToRef, and the program prints 2.

In the above, we don't know that I implements IndirectIndexWith(i32), so the program prints 1. But if we make a seemingly-unrelated change to Generic:

-class Generic(T:! type) {}
+class Generic(T:! IndirectIndexWith(i32)) {}

then F picks up an implicit constraint that T implements IndirectIndexWith(i32) then the program now prints 2.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment