| 192 | } while (false) |
| 193 | |
| 194 | static Status ValidateArg(const OpDef::ArgDef& arg, const OpDef& op_def, |
| 195 | bool output, std::set<string>* names) { |
| 196 | const string suffix = strings::StrCat( |
| 197 | output ? " for output '" : " for input '", arg.name(), "'"); |
| 198 | VALIDATE(gtl::InsertIfNotPresent(names, arg.name()), |
| 199 | "Duplicate name: ", arg.name()); |
| 200 | VALIDATE(HasAttrStyleType(arg), "Missing type", suffix); |
| 201 | |
| 202 | if (!arg.number_attr().empty()) { |
| 203 | const OpDef::AttrDef* attr = FindAttr(arg.number_attr(), op_def); |
| 204 | VALIDATE(attr != nullptr, "No attr with name '", arg.number_attr(), "'", |
| 205 | suffix); |
| 206 | VALIDATE(attr->type() == "int", "Attr '", attr->name(), "' used as length", |
| 207 | suffix, " has type ", attr->type(), " != int"); |
| 208 | VALIDATE(attr->has_minimum(), "Attr '", attr->name(), "' used as length", |
| 209 | suffix, " must have minimum"); |
| 210 | VALIDATE(attr->minimum() >= 0, "Attr '", attr->name(), "' used as length", |
| 211 | suffix, " must have minimum >= 0"); |
| 212 | VALIDATE(arg.type_list_attr().empty(), |
| 213 | "Can't have both number_attr and type_list_attr", suffix); |
| 214 | VALIDATE((arg.type() != DT_INVALID ? 1 : 0) + |
| 215 | (!arg.type_attr().empty() ? 1 : 0) == |
| 216 | 1, |
| 217 | "Exactly one of type, type_attr must be set", suffix); |
| 218 | } else { |
| 219 | const int num_type_fields = (arg.type() != DT_INVALID ? 1 : 0) + |
| 220 | (!arg.type_attr().empty() ? 1 : 0) + |
| 221 | (!arg.type_list_attr().empty() ? 1 : 0); |
| 222 | VALIDATE(num_type_fields == 1, |
| 223 | "Exactly one of type, type_attr, type_list_attr must be set", |
| 224 | suffix); |
| 225 | } |
| 226 | |
| 227 | if (!arg.type_attr().empty()) { |
| 228 | const OpDef::AttrDef* attr = FindAttr(arg.type_attr(), op_def); |
| 229 | VALIDATE(attr != nullptr, "No attr with name '", arg.type_attr(), "'", |
| 230 | suffix); |
| 231 | VALIDATE(attr->type() == "type", "Attr '", attr->name(), |
| 232 | "' used as type_attr", suffix, " has type ", attr->type(), |
| 233 | " != type"); |
| 234 | } else if (!arg.type_list_attr().empty()) { |
| 235 | const OpDef::AttrDef* attr = FindAttr(arg.type_list_attr(), op_def); |
| 236 | VALIDATE(attr != nullptr, "No attr with name '", arg.type_list_attr(), "'", |
| 237 | suffix); |
| 238 | VALIDATE(attr->type() == "list(type)", "Attr '", attr->name(), |
| 239 | "' used as type_list_attr", suffix, " has type ", attr->type(), |
| 240 | " != list(type)"); |
| 241 | } else { |
| 242 | // All argument types should be non-reference types at this point. |
| 243 | // ArgDef.is_ref is set to true for reference arguments. |
| 244 | VALIDATE(!IsRefType(arg.type()), "Illegal use of ref type '", |
| 245 | DataTypeString(arg.type()), "'. Use 'Ref(type)' instead", suffix); |
| 246 | } |
| 247 | |
| 248 | return Status::OK(); |
| 249 | } |
| 250 | |
| 251 | Status ValidateOpDef(const OpDef& op_def) { |
no test coverage detected