sem: Add BindingPoint() to sem::Variable

The Resolver already has this information, so just propagate it to the
semantic variable.

Change-Id: Id9fc58d3fc706a1433aba7cb3845b4f53f3fc386
Reviewed-on: https://dawn-review.googlesource.com/c/tint/+/55120
Auto-Submit: James Price <jrprice@google.com>
Commit-Queue: Ben Clayton <bclayton@google.com>
Kokoro: Kokoro <noreply+kokoro@google.com>
Reviewed-by: Ben Clayton <bclayton@google.com>
diff --git a/src/resolver/resolver.cc b/src/resolver/resolver.cc
index 3fa4231..4f44799 100644
--- a/src/resolver/resolver.cc
+++ b/src/resolver/resolver.cc
@@ -2863,8 +2863,9 @@
 
       sem_var = builder_->create<sem::Variable>(var, info->type, constant_id);
     } else {
-      sem_var = builder_->create<sem::Variable>(
-          var, info->type, info->storage_class, info->access);
+      sem_var =
+          builder_->create<sem::Variable>(var, info->type, info->storage_class,
+                                          info->access, info->binding_point);
     }
 
     std::vector<const sem::VariableUser*> users;
diff --git a/src/resolver/resolver_test.cc b/src/resolver/resolver_test.cc
index 0143379..facdd7f 100644
--- a/src/resolver/resolver_test.cc
+++ b/src/resolver/resolver_test.cc
@@ -2020,6 +2020,22 @@
   EXPECT_EQ(Sem().Get(var)->Access(), ast::Access::kRead);
 }
 
+TEST_F(ResolverTest, BindingPoint_SetForResources) {
+  // [[group(1), binding(2)]] var s1 : sampler;
+  // [[group(3), binding(4)]] var s2 : sampler;
+  auto* s1 = Global(Sym(), ty.sampler(ast::SamplerKind::kSampler),
+                    ast::DecorationList{create<ast::GroupDecoration>(1),
+                                        create<ast::BindingDecoration>(2)});
+  auto* s2 = Global(Sym(), ty.sampler(ast::SamplerKind::kSampler),
+                    ast::DecorationList{create<ast::GroupDecoration>(3),
+                                        create<ast::BindingDecoration>(4)});
+
+  EXPECT_TRUE(r()->Resolve()) << r()->error();
+
+  EXPECT_EQ(Sem().Get(s1)->BindingPoint(), (sem::BindingPoint{1u, 2u}));
+  EXPECT_EQ(Sem().Get(s2)->BindingPoint(), (sem::BindingPoint{3u, 4u}));
+}
+
 TEST_F(ResolverTest, Function_EntryPoints_StageDecoration) {
   // fn b() {}
   // fn c() { b(); }
diff --git a/src/sem/variable.cc b/src/sem/variable.cc
index 305b4ac..a7758dd 100644
--- a/src/sem/variable.cc
+++ b/src/sem/variable.cc
@@ -26,11 +26,13 @@
 Variable::Variable(const ast::Variable* declaration,
                    const sem::Type* type,
                    ast::StorageClass storage_class,
-                   ast::Access access)
+                   ast::Access access,
+                   sem::BindingPoint binding_point)
     : declaration_(declaration),
       type_(type),
       storage_class_(storage_class),
       access_(access),
+      binding_point_(binding_point),
       is_pipeline_constant_(false) {}
 
 Variable::Variable(const ast::Variable* declaration,
diff --git a/src/sem/variable.h b/src/sem/variable.h
index ebe9c49..55275cc 100644
--- a/src/sem/variable.h
+++ b/src/sem/variable.h
@@ -19,6 +19,7 @@
 
 #include "src/ast/access.h"
 #include "src/ast/storage_class.h"
+#include "src/sem/binding_point.h"
 #include "src/sem/expression.h"
 
 namespace tint {
@@ -43,10 +44,12 @@
   /// @param type the variable type
   /// @param storage_class the variable storage class
   /// @param access the variable access control type
+  /// @param binding_point the optional resource binding point of the variable
   Variable(const ast::Variable* declaration,
            const sem::Type* type,
            ast::StorageClass storage_class,
-           ast::Access access);
+           ast::Access access,
+           sem::BindingPoint binding_point = {});
 
   /// Constructor for overridable pipeline constants
   /// @param declaration the AST declaration node
@@ -71,6 +74,9 @@
   /// @returns the access control for the variable
   ast::Access Access() const { return access_; }
 
+  /// @returns the resource binding point for the variable
+  sem::BindingPoint BindingPoint() const { return binding_point_; }
+
   /// @returns the expressions that use the variable
   const std::vector<const VariableUser*>& Users() const { return users_; }
 
@@ -88,6 +94,7 @@
   const sem::Type* const type_;
   ast::StorageClass const storage_class_;
   ast::Access const access_;
+  sem::BindingPoint binding_point_;
   std::vector<const VariableUser*> users_;
   const bool is_pipeline_constant_;
   const uint16_t constant_id_ = 0;