private void validateSchema(FieldSchema pigField, HCatFieldSchema hcatField, 
                              Schema topLevelPigSchema, HCatSchema topLevelHCatSchema, 
                              int columnPos)
    throws HCatException, FrontendException {
    validateAlias(pigField.alias);
    byte type = pigField.type;
    if (DataType.isComplex(type)) {
      switch (type) {

      case DataType.MAP:
        if (hcatField != null) {
          if (hcatField.getMapKeyType() != Type.STRING) {
            throw new FrontendException("Key Type of map must be String " + hcatField, PigHCatUtil.PIG_EXCEPTION_CODE);
          }
          // Map values can be primitive or complex
        }
        break;

      case DataType.BAG:
        HCatSchema arrayElementSchema = hcatField == null ? null : hcatField.getArrayElementSchema();
        for (FieldSchema innerField : pigField.schema.getField(0).schema.getFields()) {
          validateSchema(innerField, getColFromSchema(pigField.alias, arrayElementSchema), 
                  topLevelPigSchema, topLevelHCatSchema, columnPos);
        }
        break;

      case DataType.TUPLE:
        HCatSchema structSubSchema = hcatField == null ? null : hcatField.getStructSubSchema();
        for (FieldSchema innerField : pigField.schema.getFields()) {
          validateSchema(innerField, getColFromSchema(pigField.alias, structSubSchema),
                  topLevelPigSchema, topLevelHCatSchema, columnPos);
        }
        break;

      default:
        throw new FrontendException("Internal Error.", PigHCatUtil.PIG_EXCEPTION_CODE);
      }
    }
    else if(hcatField != null) {
      //there is no point trying to validate further if we have no type info about target field
      switch (type) {
        case DataType.BIGDECIMAL:
          throwTypeMismatchException(type, Lists.newArrayList(Type.DECIMAL), hcatField, columnPos);
          break;
        case DataType.DATETIME:
          throwTypeMismatchException(type, Lists.newArrayList(Type.TIMESTAMP, Type.DATE), hcatField, columnPos);
          break;
        case DataType.BYTEARRAY:
          throwTypeMismatchException(type, Lists.newArrayList(Type.BINARY), hcatField, columnPos);
          break;
        case DataType.BIGINTEGER:
          throwTypeMismatchException(type, Collections.<Type>emptyList(), hcatField, columnPos);
          break;
        case DataType.BOOLEAN:
          throwTypeMismatchException(type, Lists.newArrayList(Type.BOOLEAN), hcatField, columnPos);
          break;
        case DataType.CHARARRAY:
          throwTypeMismatchException(type, Lists.newArrayList(Type.STRING, Type.CHAR, Type.VARCHAR), 
                  hcatField, columnPos);
          break;
        case DataType.DOUBLE:
          throwTypeMismatchException(type, Lists.newArrayList(Type.DOUBLE), hcatField, columnPos);
          break;
        case DataType.FLOAT:
          throwTypeMismatchException(type, Lists.newArrayList(Type.FLOAT), hcatField, columnPos);
          break;
        case DataType.INTEGER:
          throwTypeMismatchException(type, Lists.newArrayList(Type.INT, Type.BIGINT, 
                  Type.TINYINT, Type.SMALLINT), hcatField, columnPos);
          break;
        case DataType.LONG:
          throwTypeMismatchException(type, Lists.newArrayList(Type.BIGINT), hcatField, columnPos);
          break;
        default:
          throw new FrontendException("'" + type + 
                  "' Pig datatype in column " + columnPos + "(0-based) is not supported by HCat", 
                  PigHCatUtil.PIG_EXCEPTION_CODE);
      }
    }
    else {
      if(false) {
        //see HIVE-6194
      throw new FrontendException("(pigSch,hcatSchema)=(" + pigField + "," +
              "" + hcatField + ") (topPig, topHcat)=(" + topLevelPigSchema + "," +
              "" + topLevelHCatSchema + ")");
      }
    }
  }
This method encodes which Pig type can map (be stored in) to which HCat type.
@throws HCatException
@throws FrontendException
hcatalog/hcatalog-pig-adapter/src/main/java/org/apache/hive/hcatalog/pig/HCatBaseStorer.java