<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
	<id>https://homeostasis.scs.carleton.ca/wiki/index.php?action=history&amp;feed=atom&amp;title=Operating_Systems_2020W%3A_Tutorial_2</id>
	<title>Operating Systems 2020W: Tutorial 2 - Revision history</title>
	<link rel="self" type="application/atom+xml" href="https://homeostasis.scs.carleton.ca/wiki/index.php?action=history&amp;feed=atom&amp;title=Operating_Systems_2020W%3A_Tutorial_2"/>
	<link rel="alternate" type="text/html" href="https://homeostasis.scs.carleton.ca/wiki/index.php?title=Operating_Systems_2020W:_Tutorial_2&amp;action=history"/>
	<updated>2026-06-02T22:26:24Z</updated>
	<subtitle>Revision history for this page on the wiki</subtitle>
	<generator>MediaWiki 1.42.1</generator>
	<entry>
		<id>https://homeostasis.scs.carleton.ca/wiki/index.php?title=Operating_Systems_2020W:_Tutorial_2&amp;diff=22585&amp;oldid=prev</id>
		<title>Soma: Created page with &quot;In this tutorial we&#039;re going to look at how processes work at a low level: how they make system calls &amp; library calls, how C and assembly compare, and and how memory is laid o...&quot;</title>
		<link rel="alternate" type="text/html" href="https://homeostasis.scs.carleton.ca/wiki/index.php?title=Operating_Systems_2020W:_Tutorial_2&amp;diff=22585&amp;oldid=prev"/>
		<updated>2020-03-20T02:45:59Z</updated>

		<summary type="html">&lt;p&gt;Created page with &amp;quot;In this tutorial we&amp;#039;re going to look at how processes work at a low level: how they make system calls &amp;amp; library calls, how C and assembly compare, and and how memory is laid o...&amp;quot;&lt;/p&gt;
&lt;p&gt;&lt;b&gt;New page&lt;/b&gt;&lt;/p&gt;&lt;div&gt;In this tutorial we&amp;#039;re going to look at how processes work at a low level: how they make system calls &amp;amp; library calls, how C and assembly compare, and and how memory is laid out.&lt;br /&gt;
&lt;br /&gt;
If you haven&amp;#039;t already, please set up and use a VM on openstack for this work.  &lt;br /&gt;
&lt;br /&gt;
==Tasks==&lt;br /&gt;
&lt;br /&gt;
===Function calls, library calls, and system calls===&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;Note that this section mostly overlaps with question 12 from Tutorial 1.  If you worked hard on it, you can skip this section.&amp;#039;&amp;#039;&lt;br /&gt;
&lt;br /&gt;
For [http://homeostasis.scs.carleton.ca/~soma/os-2017f/code/tut1/hello.c hello.c] and [http://homeostasis.scs.carleton.ca/~soma/os-2017f/code/tut1/syscall-hello.c syscall-hello.c] do the following (&amp;lt;b&amp;gt;substituting the appropriate source file for prog.c&amp;lt;/b&amp;gt;). For example, for hello.c, you would replace all instances of &amp;quot;prog&amp;quot; in a command with &amp;quot;hello&amp;quot;.&lt;br /&gt;
&lt;br /&gt;
To download programs to your VM, use the wget command, e.g.&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
 wget https://homeostasis.scs.carleton.ca/~soma/os-2017f/code/tut1/hello.c&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
# Compile the program prog.c using &amp;lt;tt&amp;gt;gcc -O2 prog.c -o prog-dyn&amp;lt;/tt&amp;gt; and run prog-dyn.  What does it do?&lt;br /&gt;
# Statically compile and optimize prog.c by running &amp;lt;tt&amp;gt;gcc -O2 -static prog.c -o prog-static&amp;lt;/tt&amp;gt;.  How does the size compare with &amp;lt;tt&amp;gt;prog&amp;lt;/tt&amp;gt;?&lt;br /&gt;
# See what system calls prog-static produces by running &amp;lt;tt&amp;gt;strace -o syscalls-static.log ./prog-static&amp;lt;/tt&amp;gt;.  Do the same for &amp;lt;tt&amp;gt;prog-dyn&amp;lt;/tt&amp;gt;.  Which version generates more system calls?  &amp;#039;&amp;#039;&amp;#039;Note: system calls are saved in the log file syscalls-static.log.  Feel free to save them in a different file.&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
# See what library calls prog-static produces by running &amp;lt;tt&amp;gt;ltrace -o library-static.log ./prog-static&amp;lt;/tt&amp;gt;.  Do the same for &amp;lt;tt&amp;gt;prog-dyn&amp;lt;/tt&amp;gt;.  Which version generates more library calls?  (If ltrace isn&amp;#039;t installed, run &amp;lt;tt&amp;gt;sudo apt-get install ltrace&amp;lt;/tt&amp;gt;)&lt;br /&gt;
# Use the command &amp;lt;tt&amp;gt;ls -l&amp;lt;/tt&amp;gt; to see the metadata associated with prog.c and prog-dyn, and prog-static.  Who owns these files?  What group are they in?  Do you notice any pattern with the permissions (rwx) associated with each file?&lt;br /&gt;
# (optional) Look up the documentation for each of the system calls made by the static versions of the programs.  You may need to append a 2 or 3 to the manpage invocation, e.g. &amp;quot;man 2 write&amp;quot; gets you the write system call documentation.&lt;br /&gt;
&lt;br /&gt;
===Comparing C and assembly===&lt;br /&gt;
&lt;br /&gt;
Do the following with hello.c and syscall-hello.c, as before.&lt;br /&gt;
&lt;br /&gt;
A few tips on reading assembly code.  See [https://en.wikibooks.org/wiki/X86_Assembly/GAS_Syntax AT&amp;amp;T/GNU Assembler syntax] for more information on syntax and [https://en.wikipedia.org/wiki/X86_calling_conventions#System_V_AMD64_ABI the Wikipedia article on calling conventions] for how functions are called.&lt;br /&gt;
* The last letter of many instructions refers to the size of the operand.  For example, callq means call a function using a &amp;quot;quad&amp;quot; value (64 bits).&lt;br /&gt;
* A dollar sign preceding a value means that it is a literal value, a percent sign means it is a register.&lt;br /&gt;
* If a register is in parentheses, then it is being used as a &amp;quot;pointer&amp;quot; (it contains an address, so the CPU goes to that address and interacts with the memory there).  If there is a number before the parentheses, it is an offset to the register&amp;#039;s value.&lt;br /&gt;
&lt;br /&gt;
# Using the &amp;lt;tt&amp;gt;nm&amp;lt;/tt&amp;gt; command, see what symbols are defined in prog-static and prog-dyn.  Which defines more symbols?&lt;br /&gt;
# Run the command &amp;lt;tt&amp;gt;gcc -c -O2 prog.c&amp;lt;/tt&amp;gt; to produce an object file.  What file was produced?  What symbols does it define?&lt;br /&gt;
# Look at the assembly code of the program by running &amp;lt;tt&amp;gt;gcc -S -O2 prog.c&amp;lt;/tt&amp;gt;.  What file was produced?  Identify the following in the assembly code (if present):&lt;br /&gt;
#* A function call (call)&lt;br /&gt;
#* A return from a function (ret)&lt;br /&gt;
#* Registers being saved onto the stack (push)&lt;br /&gt;
#* Registers being retrieved from the stack (pop)&lt;br /&gt;
#* Subtraction (sub)&lt;br /&gt;
#* A system call (syscall)&lt;br /&gt;
# Disassemble the object file using &amp;lt;tt&amp;gt;objdump -d&amp;lt;/tt&amp;gt;.  How does this disassembly compare with the output from gcc -S?&lt;br /&gt;
# Examine the headers of object file, dynamically linked executable, and the statically linked executable using &amp;lt;tt&amp;gt;objdump -h&amp;lt;/tt&amp;gt;&lt;br /&gt;
# Examine the contents of object file, dynamically linked executable, and the statically linked executable using &amp;lt;tt&amp;gt;objdump -s&amp;lt;/tt&amp;gt;&lt;br /&gt;
# Re-run all of the previous gcc commands adding the &amp;quot;-v&amp;quot; flag.  What is all of that output?&lt;br /&gt;
&lt;br /&gt;
===Examining the runtime memory map===&lt;br /&gt;
&lt;br /&gt;
Compile and run [https://homeostasis.scs.carleton.ca/~soma/os-2019f/code/3000memview.c 3000memview.c], then consider the following questions.&lt;br /&gt;
# Why are the addresses inconsistent between runs?&lt;br /&gt;
# Roughly where does the stack seem to be?  The heap?  Code?  Global variables?&lt;br /&gt;
# Observe how the heap grows (i.e. the value of sbrk changes) in response to malloc calls.  Would you expect the heap to ever run into the stack?  Why or why not?&lt;br /&gt;
# Change each malloc call to allocate more than 128K.  What happens to the values of sbrk?  Why?  (Hint: use strace)&lt;br /&gt;
# Add more code and data to the program, and add more printf&amp;#039;s to see where things are.  Are things where you expect them to be?&lt;br /&gt;
&lt;br /&gt;
==Code==&lt;br /&gt;
&lt;br /&gt;
===hello.c===&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot; line&amp;gt;&lt;br /&gt;
#include &amp;lt;stdio.h&amp;gt;&lt;br /&gt;
&lt;br /&gt;
int main(int argc, char *argv[]) {&lt;br /&gt;
&lt;br /&gt;
        printf(&amp;quot;Hello world!\n&amp;quot;);&lt;br /&gt;
&lt;br /&gt;
        return 0;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===syscall-hello.c===&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot; line&amp;gt;&lt;br /&gt;
#include &amp;lt;unistd.h&amp;gt;&lt;br /&gt;
#include &amp;lt;sys/syscall.h&amp;gt;&lt;br /&gt;
&lt;br /&gt;
char *buf = &amp;quot;Hello world!\n&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
int main(int argc, char *argv) {&lt;br /&gt;
        size_t result;&lt;br /&gt;
&lt;br /&gt;
        /* &amp;quot;man 2 write&amp;quot; to see arguments to write syscall */&lt;br /&gt;
        result = syscall(SYS_write, 1, buf, 13);&lt;br /&gt;
&lt;br /&gt;
        return (int) result;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===3000memview.c===&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot; line&amp;gt;&lt;br /&gt;
#include &amp;lt;stdio.h&amp;gt;&lt;br /&gt;
#include &amp;lt;stdlib.h&amp;gt;&lt;br /&gt;
#include &amp;lt;unistd.h&amp;gt;&lt;br /&gt;
&lt;br /&gt;
char *gmsg = &amp;quot;Global Message&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
const int buffer_size = 100;&lt;br /&gt;
&lt;br /&gt;
int main(int argc, char *argv[], char *envp[])&lt;br /&gt;
{&lt;br /&gt;
        char *lmsg = &amp;quot;Local Message&amp;quot;;&lt;br /&gt;
        char *buf[buffer_size];&lt;br /&gt;
        int i;&lt;br /&gt;
        &lt;br /&gt;
        printf(&amp;quot;Memory report\n&amp;quot;);&lt;br /&gt;
        printf(&amp;quot;argv:      %lx\n&amp;quot;, (unsigned long) argv);&lt;br /&gt;
        printf(&amp;quot;argv[0]:   %lx\n&amp;quot;, (unsigned long) argv[0]);&lt;br /&gt;
        printf(&amp;quot;envp:      %lx\n&amp;quot;, (unsigned long) envp);&lt;br /&gt;
        printf(&amp;quot;envp[0]:   %lx\n&amp;quot;, (unsigned long) envp[0]);&lt;br /&gt;
&lt;br /&gt;
        printf(&amp;quot;lmsg:      %lx\n&amp;quot;, (unsigned long) lmsg);&lt;br /&gt;
        printf(&amp;quot;&amp;amp;lmsg:     %lx\n&amp;quot;, (unsigned long) &amp;amp;lmsg);&lt;br /&gt;
        printf(&amp;quot;gmsg:      %lx\n&amp;quot;, (unsigned long) gmsg);&lt;br /&gt;
        printf(&amp;quot;&amp;amp;gmsg:     %lx\n&amp;quot;, (unsigned long) &amp;amp;gmsg);&lt;br /&gt;
&lt;br /&gt;
        printf(&amp;quot;main:      %lx\n&amp;quot;, (unsigned long) &amp;amp;main);&lt;br /&gt;
&lt;br /&gt;
        printf(&amp;quot;sbrk(0):   %lx\n&amp;quot;, (unsigned long) sbrk(0));&lt;br /&gt;
        printf(&amp;quot;&amp;amp;buf:      %lx\n&amp;quot;, (unsigned long) &amp;amp;buf);&lt;br /&gt;
&lt;br /&gt;
        for (i = 0; i&amp;lt;buffer_size; i++) {&lt;br /&gt;
                buf[i] = (char *) malloc(4096);&lt;br /&gt;
        }&lt;br /&gt;
        &lt;br /&gt;
        printf(&amp;quot;buf[0]:    %lx\n&amp;quot;, (unsigned long) buf[0]);&lt;br /&gt;
        printf(&amp;quot;sbrk(0):   %lx\n&amp;quot;, (unsigned long) sbrk(0));&lt;br /&gt;
        &lt;br /&gt;
        return 0;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;/div&gt;</summary>
		<author><name>Soma</name></author>
	</entry>
</feed>