How to mark function argument as output
Asked Answered
N

3

14

C# allows to mark function argument as output only:

void func(out int i)
{
    i = 44;
}

Is it possible to do something similar in C/C++? This could improve optimization. Additionally is should silence out warnings "error: 'myVar' may be used uninitialized in this function", when variable is not initialized and then passed to function as output argument.

I use gcc/g++ (currently 4.4.7) to compile my code.

Edit: I know about pointers and references, this is not what I am looking for. I need something like this:

void func(int* __attribute__((out)) i)
{
    *i = 44;
}

void func2()
{
    int myVal; // gcc will print warning: 'myVar' may be used uninitialized in this function
    func(&myVal);
    //...
}

Edit 2: Some extra code is needed to reproduce warning "'myVar' may be used uninitialized in this function". Additionally you have to pass -Wall -O1 to gcc.

void __attribute__((const)) func(int* i)
{
    *i = 44;
}

int func2()
{
    int myVal; // warning here
    func(&myVal);
    return myVal;
}
Nafis answered 10/6, 2015 at 9:21 Comment(8)
Do you want pointers? Like void func(int* i){*i = 44;} (C)?Passible
C and C++ are different languages. In C++ you should use references, in C you only have pointers.Malevolent
I need additional attribute to mark ptr/ref argument as out only. I updated my question to state this.Canonicity
My g++ does not warn anything even with -Wall -Wextra -pedantic flags and even if myVal is used in func2. I'm assuming that you meant to pass the address of myVal into func.Maghutte
Please see my edit 2, some extra code plus -O1 was needed.Canonicity
Just out of pure curiosity, why do you need this ?Sprawl
Having lied to the compiler with __attribute__((const)), which promises that the function "does not examine any values except its arguments, and has no effects except the return value", you now complain that the compiler is fooled by the lie?Stegall
I think pointers are the only option for this in C/C++.Barbarity
I
14

"Is it possible to do something similar in C/C++?"

Not really. Standard c++ or c doesn't support such thing like a output only parameter.

In c++ you can use a reference parameter to get in/out semantics:

void func(int& i) {
          // ^
    i = 44;
}

For c you need a pointer, to do the same:

void func(int* i) {
          // ^ 
    *i = 44;
 // ^
}

Note that there are no distinctions between out and in&out parameters, unless you use a const reference (which means input only):

void func(const int& i) {
       // ^^^^^
    i = 44;
}
Isatin answered 10/6, 2015 at 9:23 Comment(8)
Note that there are no distinctions between out and in&out parameters.Obstipation
Unless you use const as explained in another answer ;)Malevolent
I need additional attribute to mark ptr/ref argument as out only. I updated my question to state this.Canonicity
@DanielFrużyński "I need additional attribute to mark ptr/ref argument as out only." You simply cannot in standard c++ or c.Scrogan
I know this, and I am looking for some non-standard, probably gcc-only extension.Canonicity
@DanielFrużyński "I am looking for some non-standard, probably gcc-only extension" Not that I'm aware of one. I'd say that the semantics as defined in the language standards for c++ or c, inherently won't allow such extension being implemented.Scrogan
gcc already implements additional attributes for functions, variables and types. Attribute for function argument could look like this: void func(int* __attribute__((out)) i) or void func(__attribute__((out)) int* i)Canonicity
it's such a pity C++ doesn't have an out designation, because sometimes that it the pattern and it would be super nice if the compile gave you similar warning as what you get in C# eg when you forget to set the value.Llama
M
2

When you want to pass an arg as output in C++ you pass it as a reference :

 void func(int &i)
{
    i = 44;
}

and you must initialize it before doing anything on it.

Note : You can specify when you want the arg to be just an input with a const ref :

 void func(const int &i)
{
    i = 44;
}
Millner answered 10/6, 2015 at 9:25 Comment(2)
I need additional attribute to mark ptr/ref argument as out only. I updated my question to state this.Canonicity
You just can't, you can just specify an input only, not an output onlyMillner
D
0

As others have noted, you can use a pointer or reference to pass out parameters. But there is no way to annotate whether it is in, out, or in/out.

void func(int &i); // Out or in/out. Non-nullable.
void func(int *i); // Out or in/out. Nullable.
void func(const int &i); // In. Non-nullable.
void func(const int *i); // In. Nullable.

Microsoft Compiler Extension

If using MSVC, The Microsoft Source-code Annotation Language (SAL) can provide such annotation and perform compile-time static analysis to enforce the correct usage on the caller.

void func(_Out_ int &i);
void func(_Out_ int *i);
void func(_Out_opt_ int *i);
void func(_Inout_ int &i);
void func(_Inout_ int *i);
void func(_Inout_opt_ int *i);
void func(_In_ const int &i);
void func(_In_ const int *i);
void func(_In_opt_ const int *i);
Doyenne answered 21/11, 2023 at 15:45 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.