.. _functions: ========= Functions ========= Spicy's language allows to define custom functions just like most other languages. The generic syntax for defining a function with is ``N`` parameters is:: [public] function NAME(NAME_1: TYPE_1, ..., NAME_N: TYPE_N) [: RETURN_TYPE ] { ... BODY ... } A ``public`` function will be :ref:`accessible from other modules ` . If the return type is skipped, it's implicitly taken as ``void``, i.e., the function will not return anything. If a function has return type other than void, all paths through the body must end in a :ref:`statement_return` returning a corresponding value. A parameter specification can be postfixed with a default value: ``NAME: TYPE = DEFAULT``. Callers may then omit that parameter. By default, by parameters are passed by constant reference and hence remain read-only inside the function's body. To make a parameter modifiable, with any changes becoming visible to the caller, a parameter can be prefixed with ``inout``: .. spicy-code:: function-inout.spicy module Test; global s = "1"; function foo(inout x: string) { x = "2"; } print s; foo(s); print s; .. spicy-output:: function-inout.spicy :exec: spicyc -j %INPUT .. note:: When calling a function with an ``inout`` parameter, the type of the corresponding argument must match the type of the parameter exactly. For example, while normally you can pass an integer of type `uint8` to to a parameter of type `uint64`, that doesn't work if the parameter is `inout`. Spicy has couple more function-like constructs (:ref:`unit_hooks` and :ref:`unit_parameters`) that use the same conventions for parameter passing.