static boolean isAssignableTo(ClassNode type,ClassNode toBeAssignedTo){
  if (UNKNOWN_PARAMETER_TYPE == type)   return true;
  if (type == toBeAssignedTo)   return true;
  if (toBeAssignedTo.redirect() == STRING_TYPE && type.redirect() == GSTRING_TYPE) {
    return true;
  }
  if (isPrimitiveType(toBeAssignedTo))   toBeAssignedTo=getWrapper(toBeAssignedTo);
  if (isPrimitiveType(type))   type=getWrapper(type);
  if (Double_TYPE == toBeAssignedTo) {
    return type.isDerivedFrom(Number_TYPE);
  }
  if (Float_TYPE == toBeAssignedTo) {
    return type.isDerivedFrom(Number_TYPE) && Double_TYPE != type.redirect();
  }
  if (Long_TYPE == toBeAssignedTo) {
    return type.isDerivedFrom(Number_TYPE) && Double_TYPE != type.redirect() && Float_TYPE != type.redirect();
  }
  if (Integer_TYPE == toBeAssignedTo) {
    return type.isDerivedFrom(Number_TYPE) && Double_TYPE != type.redirect() && Float_TYPE != type.redirect() && Long_TYPE != type.redirect();
  }
  if (Short_TYPE == toBeAssignedTo) {
    return type.isDerivedFrom(Number_TYPE) && Double_TYPE != type.redirect() && Float_TYPE != type.redirect() && Long_TYPE != type.redirect() && Integer_TYPE != type.redirect();
  }
  if (Byte_TYPE == toBeAssignedTo) {
    return type.redirect() == Byte_TYPE;
  }
  if (type.isArray() && toBeAssignedTo.isArray()) {
    return isAssignableTo(type.getComponentType(),toBeAssignedTo.getComponentType());
  }
  if (type.isDerivedFrom(GSTRING_TYPE) && STRING_TYPE.equals(toBeAssignedTo)) {
    return true;
  }
  if (toBeAssignedTo.isDerivedFrom(GSTRING_TYPE) && STRING_TYPE.equals(type)) {
    return true;
  }
  if (implementsInterfaceOrIsSubclassOf(type,toBeAssignedTo)) {
    if (OBJECT_TYPE.equals(toBeAssignedTo))     return true;
    if (toBeAssignedTo.isUsingGenerics()) {
      GenericsType gt=GenericsUtils.buildWildcardType(toBeAssignedTo);
      return gt.isCompatibleWith(type);
    }
    return true;
  }
  if (type.isDerivedFrom(CLOSURE_TYPE) && isSAMType(toBeAssignedTo)) {
    return true;
  }
  return false;
}

static boolean isAssignableTo ( ClassNode type , ClassNode toBeAssignedTo ) { if ( UNKNOWN_PARAMETER_TYPE == type ) return true ; if ( type == toBeAssignedTo ) return true ; if ( toBeAssignedTo . redirect ( ) == STRING_TYPE && type . redirect ( ) == GSTRING_TYPE ) { return true ; } if ( isPrimitiveType ( toBeAssignedTo ) ) toBeAssignedTo = getWrapper ( toBeAssignedTo ) ; if ( isPrimitiveType ( type ) ) type = getWrapper ( type ) ; if ( Double_TYPE == toBeAssignedTo ) { return type . isDerivedFrom ( Number_TYPE ) ; } if ( Float_TYPE == toBeAssignedTo ) { return type . isDerivedFrom ( Number_TYPE ) && Double_TYPE != type . redirect ( ) ; } if ( Long_TYPE == toBeAssignedTo ) { return type . isDerivedFrom ( Number_TYPE ) && Double_TYPE != type . redirect ( ) && Float_TYPE != type . redirect ( ) ; } if ( Integer_TYPE == toBeAssignedTo ) { return type . isDerivedFrom ( Number_TYPE ) && Double_TYPE != type . redirect ( ) && Float_TYPE != type . redirect ( ) && Long_TYPE != type . redirect ( ) ; } if ( Short_TYPE == toBeAssignedTo ) { return type . isDerivedFrom ( Number_TYPE ) && Double_TYPE != type . redirect ( ) && Float_TYPE != type . redirect ( ) && Long_TYPE != type . redirect ( ) && Integer_TYPE != type . redirect ( ) ; } if ( Byte_TYPE == toBeAssignedTo ) { return type . redirect ( ) == Byte_TYPE ; } if ( type . isArray ( ) && toBeAssignedTo . isArray ( ) ) { return isAssignableTo ( type . getComponentType ( ) , toBeAssignedTo . getComponentType ( ) ) ; } if ( type . isDerivedFrom ( GSTRING_TYPE ) && STRING_TYPE . equals ( toBeAssignedTo ) ) { return true ; } if ( toBeAssignedTo . isDerivedFrom ( GSTRING_TYPE ) && STRING_TYPE . equals ( type ) ) { return true ; } if ( implementsInterfaceOrIsSubclassOf ( type , toBeAssignedTo ) ) { if ( OBJECT_TYPE . equals ( toBeAssignedTo ) ) return true ; if ( toBeAssignedTo . isUsingGenerics ( ) ) { GenericsType gt = GenericsUtils . buildWildcardType ( toBeAssignedTo ) ; return gt . isCompatibleWith ( type ) ; } return true ; } if ( type . isDerivedFrom ( CLOSURE_TYPE ) && isSAMType ( toBeAssignedTo ) ) { return true ; } return false ; }
checks if a class node is assignable to another . this is used for example in assignment checks where you want to verify that the assignment is valid .
