コード例 #1
0
ファイル: c_typecheck_type.cpp プロジェクト: dcattaruzza/cbmc
void c_typecheck_baset::typecheck_code_type(code_typet &type)
{
  // the return type is still 'subtype()'
  type.return_type()=type.subtype();
  type.remove_subtype();

  code_typet::parameterst &parameters=type.parameters();

  // if we don't have any parameters, we assume it's (...)
  if(parameters.empty())
  {
    type.make_ellipsis();
  }
  else // we do have parameters
  {
    // is the last one ellipsis?
    if(type.parameters().back().id()==ID_ellipsis)
    {
      type.make_ellipsis();
      type.parameters().pop_back();
    }

    parameter_map.clear();

    for(auto &param : type.parameters())
    {
      // turn the declarations into parameters
      if(param.id()==ID_declaration)
      {
        ansi_c_declarationt &declaration=
          to_ansi_c_declaration(param);

        code_typet::parametert parameter;

        // first fix type
        typet &type=parameter.type();
        type=declaration.full_type(declaration.declarator());
        std::list<codet> tmp_clean_code;
        tmp_clean_code.swap(clean_code); // ignore side-effects
        typecheck_type(type);
        tmp_clean_code.swap(clean_code);
        adjust_function_parameter(type);

        // adjust the identifier
        irep_idt identifier=declaration.declarator().get_name();

        // abstract or not?
        if(identifier==irep_idt())
        {
          // abstract
          parameter.add_source_location()=declaration.type().source_location();
        }
        else
        {
          // make visible now, later parameters might use it
          parameter_map[identifier]=type;
          parameter.set_base_name(declaration.declarator().get_base_name());
          parameter.add_source_location()=
            declaration.declarator().source_location();
        }

        // put the parameter in place of the declaration
        param.swap(parameter);
      }
    }

    parameter_map.clear();

    if(parameters.size()==1 &&
       follow(parameters[0].type()).id()==ID_empty)
    {
      // if we just have one parameter of type void, remove it
      parameters.clear();
    }
  }

  typecheck_type(type.return_type());

  // 6.7.6.3:
  // "A function declarator shall not specify a return type that
  // is a function type or an array type."

  const typet &return_type=follow(type.return_type());

  if(return_type.id()==ID_array)
  {
    error().source_location=type.source_location();
    error() << "function must not return array" << eom;
    throw 0;
  }

  if(return_type.id()==ID_code)
  {
    error().source_location=type.source_location();
    error() << "function must not return function type" << eom;
    throw 0;
  }
}
コード例 #2
0
void c_typecheck_baset::typecheck_code_type(code_typet &type)
{
  code_typet::parameterst &parameters=type.parameters();
  
  // if we don't have any parameters, we assume it's (...)
  if(parameters.empty())
  {
    type.make_ellipsis();
  }
  else
  {
    // we do have parameters
    
    parameter_map.clear();
  
    for(unsigned i=0; i<type.parameters().size(); i++)
    {
      code_typet::parametert &parameter=type.parameters()[i];

      // first fix type
      typet &type=parameter.type();

      typecheck_type(type);
      
      adjust_function_parameter(type);
      
      // adjust the identifier

      irep_idt identifier=parameter.get_identifier();

      if(identifier!=irep_idt())
      {
        identifier=add_language_prefix(identifier);
    
        id_replace_mapt::const_iterator
          m_it=id_replace_map.find(identifier);

        if(m_it!=id_replace_map.end())
          identifier=m_it->second;

        parameter.set_identifier(identifier);

        // make visible now, later parameters might use it
        parameter_map[identifier]=type;
      }
    }
    
    parameter_map.clear();
  
    if(parameters.size()==1 &&
       follow(parameters[0].type()).id()==ID_empty)
    {
      // if we just have one parameter of type void, remove it
      parameters.clear();
    }
  }

  typecheck_type(type.return_type());
  
  // 6.7.6.3:
  // "A function declarator shall not specify a return type that
  // is a function type or an array type."
  
  const typet &return_type=follow(type.return_type());
  
  if(return_type.id()==ID_array)
  {
    err_location(type);
    throw "function must not return array";
  }
  
  if(return_type.id()==ID_code)
  {
    err_location(type);
    throw "function must not return function type";
  }
}