Subroutines Parameter Passing Generic Subroutines
Principles of Programming Languages
Ting Zhang Iowa State University Computer Science Department
Lecture Note 13 Oct 22, 2009 Control Abstraction: Subroutines
1 / 26
Principles of Programming Languages
Subroutines Parameter Passing Generic Subroutines
Outline
1 Subroutines
2 Parameter Passing
3 Generic Subroutines
2 / 26
Principles of Programming Languages
Subroutines Parameter Passing Generic Subroutines
Stack Layout
Typical stack layout with subroutine nest-ing:Given the calling se-quence A, E, B, D, C, in that order, frames will be allocated on the stack as shown at right, with the indicated static and dynamic links.
3 / 26
Principles of Programming Languages
Subroutines Parameter Passing Generic Subroutines
Stack Frame
A typical stack frame: Arguments are ac-cessed at positive offsets from the fp. Local variables and temporaries are ac-cessed at negative offsets from thefp. Ar-guments to be passed to called routines are assembled at the top of the frame, using positive offsets from thesp.
4 / 26
Subroutines Parameter Passing Generic Subroutines
Static Chain Maintainence
In languages with nested subroutines, the maintenance of the static chain must be performed by the caller, rather than the callee
The callee is nested (directly) inside the caller.
The caller therefore passes its own frame pointer as the callee’s static link.
The callee is k≥0 scopes “outward”-closer to the outer level of lexical nesting.
The caller dereferences its own static link k times and passes the result as the callee’s static link.
5 / 26
Principles of Programming Languages
Subroutines Parameter Passing Generic Subroutines
Typical Calling Sequence
Caller’s task before the call:saves any caller-saves registers
computes the values of arguments and moves them into the stack or registers
computes the static link (if needed) and passes it as an extra, hidden argument
jump to the subroutine, simultaneously passing the return address on the stack or in a register
Callee’s task before the execution:
allocates a frame by subtracting an appropriate constant from thesp saves the old frame pointer into the stack, and assigns it an appropriate new value
saves any callee-saves registers that may be overwritten by the current routine
6 / 26
Principles of Programming Languages
Subroutines Parameter Passing Generic Subroutines
Typical Calling Sequence
Callee’s after the execution:moves the return value (if any) into a register or a reserved location in the stack
restores callee-saves registers if needed restores thefpand thesp jumps back to the return address Caller’s task after the call:
moves the return value to wherever it is needed restores caller-saves registers if needed
7 / 26
Principles of Programming Languages
Subroutines Parameter Passing Generic Subroutines
Frame Allocation
A stack-frame is created merely by moving the stack pointer up by d locations at the start of a subroutine
8 / 26
Subroutines Parameter Passing Generic Subroutines
Frame Growth
9 / 26
Principles of Programming Languages
Subroutines Parameter Passing Generic Subroutines
Outline
1 Subroutines
2 Parameter Passing
3 Generic Subroutines
10 / 26
Principles of Programming Languages
Subroutines Parameter Passing Generic Subroutines
Parameter Passing
Parameter passing modes: In
Out In/Out
Parameter passing mechanisms: Call by value (in) Call by reference (in+out) Call by result (out) Call by value/result (in+out) Call by name (in+out) Call by need (in+out)
11 / 26
Principles of Programming Languages
Subroutines Parameter Passing Generic Subroutines
Call by Value
Representative language: C
Actual parameters are evaluated and their values are assigned to the formal parameters
Actual parameters arenotaffected by the change to the formal parameters
Data can only be modified by passing pointers to the data swap(int *a, int *b) {
int t = *a; *a = *b; *b = t; }
12 / 26
Subroutines Parameter Passing Generic Subroutines
Call by Reference
Representative language: Fortran SUBROUTINE SWAP(A,B) INTEGER A, B, C C=A A=B B=C END
If an R-value appears as an argument, a temporary variable is created to hold the value, and this variable is passed by reference SWAP(A,2)
is equivalent to A = 2
13 / 26
Principles of Programming Languages
Subroutines Parameter Passing Generic Subroutines
Call by Value/Reference
Provides call-by-value as well as call-by-referenceRepresentative language: Pascal, C++ Call by value is similar to C
Call by reference is indicated by additional qualifiers In Pascal:
procedure swap(var a:integer, var b:integer) var t; begin t := a; a := b; b := t end In C++: void swap(int& a, int& b) int t; begin t := a; a := b; b := t end 14 / 26
Principles of Programming Languages
Subroutines Parameter Passing Generic Subroutines
Call by Sharing
Acts as “call-by-value” for the immutable objects and “call-by-reference” for mutable objects. Also calledcall-by-objectRepresentative language: Python, Java, C#
Behaves like call-by-value for immutable objects in assignments Behaves like call-by-reference for mutable objects Immutable objects in Python:
str = "cannot be changed" def change(par):
par = "change" change(str)
Mutable objects in Python: lst = ["can", "be", "changed"] def change(par):
par.append("sure") change(lst)
15 / 26
Principles of Programming Languages
Subroutines Parameter Passing Generic Subroutines
Call by Result
Representative language: AdaThe value of the formal parameter is copied into the actual parameter when the subroutine returns
x : integer
procedure foo(y : out integer) y := 3 print x . . . x := 2 foo(x) print x
If y is passed by reference the program will print 3 twice. If y is passed by value/result, it will print 2 and then 3
16 / 26
Subroutines Parameter Passing Generic Subroutines
Call by Name
Representative language: Algol 60
The actual arguments are not evaluated at all; they are substituted into the function body directly
integer i;
real procedure sum (i, lo, hi, term); value lo, hi; integer i, lo, hi; real term; begin
real temp; temp := 0;
for i := lo step 1 until hi do temp := temp + term; sum := temp end;
print (sum (i, 1, 100, 1/i))
It computes the 100th harmonic number by the formula H100=
100 P i=1 1 i 17 / 26
Principles of Programming Languages
Subroutines Parameter Passing Generic Subroutines
Call by Need
Representative language: Haskell
A memorized version of call-by-name; if the function argument is evaluated, that value is stored for subsequent uses Call by name: 3 evaluations
doub x = x + x doub (doub 8) = doub 8 + doub 8 = 8 + 8 + 8 + 8 = 32
Call by need: 2 evaluations doub x = x + x doub (doub 8) = doub 8 + doub 8 = 8 + 8 + doub 8 = 16 + 16 = 32 18 / 26
Principles of Programming Languages
Subroutines Parameter Passing Generic Subroutines
Closures as Parameters
A closure (a reference to a subroutine, together with its referencing environment) can be passed as a parameter
In Standard Pascal:
A : array [low..high : integer] of integer; procedure apply_to_A(function f(n : integer) : integer);
var i : integer; begin
for i := low to high do A[i] := f(A[i]); end;
In C and C++: int A[50];
void apply_to_A(int (*f)(int)) { int i;
for (i = 0; i < sizeof(A); i++) A[i] = f(A[i]); }
19 / 26
Principles of Programming Languages
Subroutines Parameter Passing Generic Subroutines
Conformant Arrays
A formal array parameter whose shape is finalized at run timeLanguages that support conformant arrays include : Ada, Pascal In Standard Pascal:
procedure apply_to_A(function f(n : integer) : integer; A : array [low..high : integer] of integer); var i : integer;
begin for i := low to high do A[i] := f(A[i]); end; C passes only pointers to arrays to functions and array size has to be determined using some other means (e.g. as another parameter) void apply_to_A(int (*f)(int), int A[], int size_of_A) {
int i;
for (i = 0; i < size_of_A; i++) A[i] = f(A[i]); }
What is made harder in a language with non-conformant arrays? 20 / 26
Subroutines Parameter Passing Generic Subroutines
Default Parameters
A default parameter is one that need not necessarily be provided by the caller
Languages that support default parameters include : Ada, C++, Common Lisp, Python
When an actual parameter is missing, a preestablished default value will be used instead
Example in C++:
void print_num(int n, int base = 10) ... Example in Python: def function(data=[]): data.append(1) return data 21 / 26
Principles of Programming Languages
Subroutines Parameter Passing Generic Subroutines
Named Parameters
Named parameter (aka keyword parameter) explicitly binds the actual parameter to the formal parameter
Languages that support named parameters include : Ada, Modula-3, Common Lisp, and Python
Good for documentation of the purpose of parameters format_page(columns => 2,window_height => 400,
window_width => 200, header_font => Helvetica, ..., background_color => white);
Allows default parameters anywhere in formal parameter list format_page(window_width => 200);
22 / 26
Principles of Programming Languages
Subroutines Parameter Passing Generic Subroutines
Variable-length Arguments
Languages that support variable-length arguments include : C,C++,Java,C#, PythonVariable number of arguments in C and C++ is not type safe int printf(char *format, ...)
Java supports typed variable argument lists via the <type-name>...syntax
static void print_lines(String foo, String... lines)
C# allows typed variable argument lists via theparamskeyword
static void print_lines(String foo, params String[] lines) Python takes variable argument lists via the asterisk operator (*) def foo(*args):
print("Number of arguments:", len(args)) print("Arguments are: ", args)
23 / 26
Principles of Programming Languages
Subroutines Parameter Passing Generic Subroutines
Outline
1 Subroutines
2 Parameter Passing
3 Generic Subroutines
24 / 26
Subroutines Parameter Passing Generic Subroutines
Generic Subroutines and Modules
Generic Parameters Options: Java and C# pass only types
Ada and C++ allow values of ordinary (nongeneric) types, including subroutines and classes
Implementation Options:
Ada and C++ use a purely static mechanism: the compiler creates a separate copy of the code for every instance
Java guarantees that all instances of a given generic will share the same code at run time
C# uses different implementations for different built-in or value types while maintaining type safety
25 / 26
Principles of Programming Languages
Subroutines Parameter Passing Generic Subroutines
Generic Parameter Constraints
In Java one requires that a generic parameter support a particular set of methodspublic static <T extends Comparable<T>> void sort(T A[]) { ...
if (A[i].compareTo(A[j]) >= 0) ... ...
}
Same in C# in a different syntax
static void sort<T>(T[] A) where T : IComparable { ...
if (A[i].CompareTo(A[j]) >= 0) ... ...
}
C++ does not impose explicit constraints
26 / 26