blob: 3798b1fc79c20cc671ee501f5ed7d2f453192f2f [file] [log] [blame]
dslomovf1296572017-08-22 16:29:06 +02001// Copyright 2017 The Bazel Authors. All rights reserved.
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7// http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14package com.google.devtools.build.lib.packages;
15
16import com.google.common.collect.ImmutableCollection;
17import com.google.common.collect.ImmutableMap;
cparsons6c1c0662018-02-05 02:01:28 -080018import com.google.common.collect.ImmutableSet;
dslomovf1296572017-08-22 16:29:06 +020019import com.google.devtools.build.lib.events.Location;
cparsons6c1c0662018-02-05 02:01:28 -080020import com.google.devtools.build.lib.syntax.EvalException;
21import com.google.devtools.build.lib.syntax.FuncallExpression;
22import com.google.devtools.build.lib.syntax.FuncallExpression.MethodDescriptor;
dslomovf1296572017-08-22 16:29:06 +020023import java.util.Map;
24
25/** Base class for native implementations of {@link Info}. */
26// todo(vladmos,dslomov): make abstract once DefaultInfo stops instantiating it.
27public class NativeInfo extends Info {
28 protected final ImmutableMap<String, Object> values;
29
cparsons6c1c0662018-02-05 02:01:28 -080030 // Initialized lazily.
31 private ImmutableSet<String> fieldNames;
32
dslomovf1296572017-08-22 16:29:06 +020033 @Override
cparsons6c1c0662018-02-05 02:01:28 -080034 public Object getValue(String name) throws EvalException {
35 if (values.containsKey(name)) {
36 return values.get(name);
37 } else if (hasField(name)) {
38 MethodDescriptor methodDescriptor = FuncallExpression.getStructField(this.getClass(), name);
cparsons48032932018-04-18 09:39:02 -070039 try {
40 return FuncallExpression.invokeStructField(methodDescriptor, name, this);
41 } catch (InterruptedException exception) {
42 // Struct fields on NativeInfo objects are supposed to behave well and not throw
43 // exceptions, as they should be logicless field accessors. If this occurs, it's
44 // indicative of a bad NativeInfo implementation.
45 throw new IllegalStateException(
46 String.format("Access of field %s was unexpectedly interrupted, but should be "
47 + "uninterruptible. This is indicative of a bad provider implementation.", name));
48 }
cparsons6c1c0662018-02-05 02:01:28 -080049 } else {
50 return null;
51 }
dslomovf1296572017-08-22 16:29:06 +020052 }
53
54 @Override
brandjond331fa72017-12-28 07:38:31 -080055 public boolean hasField(String name) {
cparsons6c1c0662018-02-05 02:01:28 -080056 return getFieldNames().contains(name);
dslomovf1296572017-08-22 16:29:06 +020057 }
58
59 @Override
brandjond331fa72017-12-28 07:38:31 -080060 public ImmutableCollection<String> getFieldNames() {
cparsons6c1c0662018-02-05 02:01:28 -080061 if (fieldNames == null) {
62 fieldNames = ImmutableSet.<String>builder()
63 .addAll(values.keySet())
64 .addAll(FuncallExpression.getStructFieldNames(this.getClass()))
65 .build();
66 }
67 return fieldNames;
dslomovf1296572017-08-22 16:29:06 +020068 }
69
cparsons2415cb42018-05-01 10:32:30 -070070 public NativeInfo(Provider provider) {
cparsonse70aafe2018-02-28 12:16:38 -080071 this(provider, Location.BUILTIN);
dslomovf1296572017-08-22 16:29:06 +020072 }
73
cparsons2415cb42018-05-01 10:32:30 -070074 public NativeInfo(Provider provider, Location loc) {
cparsonse70aafe2018-02-28 12:16:38 -080075 this(provider, ImmutableMap.of(), loc);
76 }
77
cparsonsdcd0abc2018-06-21 10:13:53 -070078 // TODO(cparsons): Remove this constructor once ToolchainInfo stops using it.
cparsonse70aafe2018-02-28 12:16:38 -080079 @Deprecated
cparsons2415cb42018-05-01 10:32:30 -070080 public NativeInfo(Provider provider, Map<String, Object> values, Location loc) {
brandjonb5494572018-01-11 13:35:54 -080081 super(provider, loc);
dslomovf1296572017-08-22 16:29:06 +020082 this.values = copyValues(values);
83 }
dslomovf1296572017-08-22 16:29:06 +020084}