static int parameterSize(ParameterType parameterType) {
    switch (parameterType.nativeType()) {
      case SCHAR:
      case UCHAR:
      case SSHORT:
      case USHORT:
      case SINT:
      case UINT:
      case SLONG:
      case ULONG:
      case POINTER:
      case FLOAT:
        return 4;

      case SLONG_LONG:
      case ULONG_LONG:
      case DOUBLE:
        return 8;

      default:
        throw new IllegalArgumentException("invalid parameter type" + parameterType);
    }
  }
  boolean canCompile(
      ResultType returnType, ParameterType[] parameterTypes, CallingConvention convention) {

    switch (returnType.nativeType()) {
      case VOID:
      case SCHAR:
      case UCHAR:
      case SSHORT:
      case USHORT:
      case SINT:
      case UINT:
      case SLONG:
      case ULONG:
      case SLONG_LONG:
      case ULONG_LONG:
      case FLOAT:
      case DOUBLE:
      case POINTER:
        break;

      default:
        return false;
    }

    // There is only one calling convention; SYSV, so abort if someone tries to use stdcall
    if (convention != CallingConvention.DEFAULT) {
      return false;
    }

    int fCount = 0;
    int iCount = 0;

    for (ParameterType t : parameterTypes) {
      switch (t.nativeType()) {
        case SCHAR:
        case UCHAR:
        case SSHORT:
        case USHORT:
        case SINT:
        case UINT:
        case SLONG:
        case ULONG:
        case SLONG_LONG:
        case ULONG_LONG:
        case POINTER:
          ++iCount;
          break;

        case FLOAT:
        case DOUBLE:
          ++fCount;
          break;

        default:
          // Fail on anything else
          return false;
      }
    }

    // We can only safely compile methods with up to 6 integer and 8 floating point parameters
    return true;
  }