# .ARGTYP() and .ARGSIZ()
> [HTML Version](argtyp_and_argsiz().htm)
_Reviewed and revised April 2024_
Syntax one:
**.ARGTYP(argno)** or **.ARGTYP(@arg)**
Syntax two:
**.ARGSIZ(argno)** or **.ARGSIZ(@arg)**
These two dot functions return the type and size, respectively, of the specified source argument as passed to the current SBX, function, or procedure. Note that the original source argument types and sizes may be completely different from those received by the SBX or function; see [Parameter Types](parameter-types-xs.htm.md). These functions allow the called routine to see the original passed types and sizes before they were converted by the calling operation.
**Warning**: It is easy to accidentally specify _arg_ when you meant _@arg_, both of which are syntactically correct (assuming _arg_ is the name of an argument in the current context) but have vastly different meaning. To help avoid this mistake, the compiler (as of edit 1065) will treat _arg_ as an error if it matches a current argument name; if you really meant to reference the argument by number, use a literal number or a variable that isn't a current argument.
**Parameters**
Note that these parameters apply to all of the .ARG... functions.
_argno_ ([Unsigned int](integer-unsigned.htm.md)) \[in\]
The ordinal number of the argument being queried, starting from 1. Note that in the case of [Named Parameters](namedparameters.htm.md), the parameter numbers are determined by the function declaration or subroutine DEFXCALL directive, not necessarily by the order specified in the calling statement. If the _argno_ passed is invalid, the return value of the function will be -1.
_@arg_ (Literal parameter name) \[in\]
This syntax provides an alternate way to reference the parameter of interest by its name rather than its ordinal number. The concept is similar to that used for XPUTARG _@arg_ : _@arg_ is treated by the compiler as a macro for the argument number corresponding to the argument _arg_ as defined in the function/procedure definition or as retrieved in an SBX using XGETARG(S).
The return value for .ARGSIZ() is the size of the original argument in bytes.
The return value for .ARGTYP() is a 16-bit bitmap value based on the following tables: one bit from the first table, zero or more bits from the second table.
| **Symbol** | **Value** | **Description** |
|------|------|------|
| ARGTYP\_MASK | \&h000f | mask for types X,S,F,B,I |
| ARGTYP\_X | \&h0000 | X type (mutually exclusive) |
| ARGTYP\_S | \&h0002 | S type (" " ") |
| ARGTYP\_F | \&h0004 | F type (" " ") |
| ARGTYP\_B | \&h0006 | B type (" " ") |
| ARGTYP\_I | \&h0008 | I type (" " ") |
| **Symbol** | **Value** | **Description** |
|------|------|------|
| ARGTYP\_ARRAY | \&h0010 | Array |
| ARGTYP\_NOSURR | \&h0020 | No surrogate |
| ARGTYP\_DYN | \&h0040 | Dynamic variable |
| ARGTYP\_LOCAL | \&h0080 | Local dynamic variable |
| ARGTYP\_SBR | \&h0100 | Variable within SBX or XCALL ASHELL |
| ARGTYP\_DIMX | \&h0200 | Base of DIMX array passed by reference |
| ARGTYP\_READONLY | \&h0400 | See ARGTYP\_READONLY section below |
| ARGTYP\_COLL | \&h0800 | Collection (e.g. ordered map, etc.) |
| ARGTYP\_DYNSTRUCT | \&h1000 | Parameter is a dynstruct |
| ARGTYP\_DEFVAL | \&h2000 | Parameter is not actually passed, is set per =defval logic |
u **ARGTYP\_READONLY Details**
This flag will be set if the passed argument is a literal value, expression, or otherwise incapable of receiving an updated value. This provides a good way for routines to be able to decide whether it is worth generating and returning values for output parameters. For example:
Function Fn'Foo(arg1=0 as b2, arg2="" as s0, arg3=-1 as f6)
...
\! calc and return arg3 if not readonly
if not (.ARGTYP(@arg3) and ARGTYP\_READONLY) then
.xputarg @arg3
endif
...
The ARGTYP\_READONLY flag is set by the runtime system and is independent of the compiler version. Runtime versions prior to its implementation (see History below) will never set the flag and thus logic like that above would always calculate and output the parameter—i.e. dependability over optimization. Also note that in the above example, the use of default values in the function declaration will guarantee that the function receives three parameters, so the .ARGCNT dot variable will not help identify un-passed parameters. Instead, you may want to use the [.ARG\_PASSED()](arg_passed().htm.md) function to avoid wasting time, however harmlessly, generating return values for parameters that were not passed.
**Example: SBX**
xgetargs color, rvalue, gvalue, bvalue
xgetarg 5, name
...
if .argtyp(@gvalue) and ARGTYP\_B then ... \! if gvalue arg binary
if .argtyp(3) and ARGTYP\_B then ... \! if 3rd arg binary (same as above)
if .argtyp(@name) and ARGTYP\_S then ... \! if name arg string
The above example illustrates that in the case of an SBX, the _@arg_ reference is based on the order that the referenced variable appears in the xgetargs statement, or the argument number associated with it in a preceding xgetarg statement. Usually the _@arg_ syntax is preferred, since it self-adjusts if you alter the parameter list, but in some cases it might be preferable to stick with the numeric argument numbering.
Note that .argtyp() returns the type of the argument that was passed in the XCALL, not the type of the variable receiving it in the SBX.
For example, if the gvalue variable inside the SBX was mapped as B,1, but the SBX was called via...
xcall RGB, \&h0080ff, "255", "128", 0, "orange"
then .argtyp(@gvalue) would return \&h0422 (ARGTYP\_READONLY, ARGTYP\_NOSURR, ARGTYP\_S), not ARGTYP\_B.
**Example: Function**
map1 lastname\$,s,35,"Ryan"
call Fn'MilitaryID(serial=123456789, name=lastname\$)
...
Function Fn'MilitaryID(name="" as s20, rank="Private" as s15, serial="" as s10)
map1 ix,i,2
for ix = 1 to .argcnt
? "\&h";Fn'Dec2Hex\$(.argtyp(ix), .argsiz(ix)
next ix
EndFunction
The above should print out:
\&h22 35
\&h422 7
\&h424 8
The .argcnt is 3 even though only two parameters were listed in the call; this is because the default values in the function declaration caused the compiler to add the missing parameter and default value (rank="Private") to the call.
All three of the arguments have the ARGTYP\_NOSURR bit set, indicating that the arguments were passed directly without the use of an intermediate surrogate; that typically only affects internal subroutines passing F6 parameters with an IEEE F8 surrogate. The last two have the ARGTYP\_READONLY bit set since they were passed as expressions rather than variables and therefore can't be updated.
The first line/argument in the display refers to the name parameter (#1 in the declaration) even though it is passed second in the call. Again, the named parameter mechanism causes the calling statement to be rearranged to match up with the expectation of the target function. Note that its size is 35 (the size of the source variable lastname\$) rather than 20 (the size of the local variable name receiving it.) It can be updated via xputarg since a real variable was passed.
The second line refers to the rank parameter (#2 in the declaration); its size is 7 because it is effectively a literal string "Private".
The third line refers to the serial parameter (#3 in the declaration); its size is 8 because the value 12345678 passed in the call was converted to a numeric (F8) expression before being converted to a string during the parameter passing.
**See Also**
• .[ARGCNT](argcnt.htm.md)
• [Named Parameters](namedparameters.htm.md)
• [XGETARG(s) ](xgetarg_xgetargs.htm.md)[and](xgetarg_xgetargs.htm.md)[ XPUTARG](xgetarg_xgetargs.htm.md)
• [.ARGTYP\_READONly()](argtype_readonly.htm.md) and [.ARG\_PASSED()](arg_passed().htm.md)
**History**
2024 December, A-Shell 7.0.1767, compiler edit 1051: ARGTYP\_DYNSTRUCT and ARGTYP\_DEFVAL defined
2017 September, A-shell 6.5.1616, compiler edit 834: Add support for .ARGTYP() and .ARGSIZ().
2017 July, A-Shell 6.4.1553: ARGTYP\_READONLY added to A-Shell.
2014 September, A-Shell 6.1.1373: Functions added to A-Shell. **Warning:** These functions are not recognized by prior runtime versions, and will simply return the value of the _argno_ passed. You could use this fact to test if the feature is supported at runtime by passing an illegal _argno_, such as 999 or -2, to .ARGTYP(). If supported, the return value will be -1 (error); else if will match the _argno_ passed. If developing code that might possibly have to run on such an old version, use [MX\_GETVER](mx_getver.htm.md) or the wrapper function [Fn'MinAshVer() in fnminsasver.bsi in SOSLIB:\[907,10\]](https://bitbucket.org/microsabio/soslib/src/master/907010/fnminasver.bsi) to check the version first.