\documentclass[10pt,a4paper]{article} % Packages \usepackage{fancyhdr} % For header and footer \usepackage{multicol} % Allows multicols in tables \usepackage{tabularx} % Intelligent column widths \usepackage{tabulary} % Used in header and footer \usepackage{hhline} % Border under tables \usepackage{graphicx} % For images \usepackage{xcolor} % For hex colours %\usepackage[utf8x]{inputenc} % For unicode character support \usepackage[T1]{fontenc} % Without this we get weird character replacements \usepackage{colortbl} % For coloured tables \usepackage{setspace} % For line height \usepackage{lastpage} % Needed for total page number \usepackage{seqsplit} % Splits long words. %\usepackage{opensans} % Can't make this work so far. Shame. Would be lovely. \usepackage[normalem]{ulem} % For underlining links % Most of the following are not required for the majority % of cheat sheets but are needed for some symbol support. \usepackage{amsmath} % Symbols \usepackage{MnSymbol} % Symbols \usepackage{wasysym} % Symbols %\usepackage[english,german,french,spanish,italian]{babel} % Languages % Document Info \author{yueqiao} \pdfinfo{ /Title (cs107-computer-organization-and-systems.pdf) /Creator (Cheatography) /Author (yueqiao) /Subject (CS107 Computer Organization and Systems Cheat Sheet) } % Lengths and widths \addtolength{\textwidth}{6cm} \addtolength{\textheight}{-1cm} \addtolength{\hoffset}{-3cm} \addtolength{\voffset}{-2cm} \setlength{\tabcolsep}{0.2cm} % Space between columns \setlength{\headsep}{-12pt} % Reduce space between header and content \setlength{\headheight}{85pt} % If less, LaTeX automatically increases it \renewcommand{\footrulewidth}{0pt} % Remove footer line \renewcommand{\headrulewidth}{0pt} % Remove header line \renewcommand{\seqinsert}{\ifmmode\allowbreak\else\-\fi} % Hyphens in seqsplit % This two commands together give roughly % the right line height in the tables \renewcommand{\arraystretch}{1.3} \onehalfspacing % Commands \newcommand{\SetRowColor}[1]{\noalign{\gdef\RowColorName{#1}}\rowcolor{\RowColorName}} % Shortcut for row colour \newcommand{\mymulticolumn}[3]{\multicolumn{#1}{>{\columncolor{\RowColorName}}#2}{#3}} % For coloured multi-cols \newcolumntype{x}[1]{>{\raggedright}p{#1}} % New column types for ragged-right paragraph columns \newcommand{\tn}{\tabularnewline} % Required as custom column type in use % Font and Colours \definecolor{HeadBackground}{HTML}{333333} \definecolor{FootBackground}{HTML}{666666} \definecolor{TextColor}{HTML}{333333} \definecolor{DarkBackground}{HTML}{A3A3A3} \definecolor{LightBackground}{HTML}{F3F3F3} \renewcommand{\familydefault}{\sfdefault} \color{TextColor} % Header and Footer \pagestyle{fancy} \fancyhead{} % Set header to blank \fancyfoot{} % Set footer to blank \fancyhead[L]{ \noindent \begin{multicols}{3} \begin{tabulary}{5.8cm}{C} \SetRowColor{DarkBackground} \vspace{-7pt} {\parbox{\dimexpr\textwidth-2\fboxsep\relax}{\noindent \hspace*{-6pt}\includegraphics[width=5.8cm]{/web/www.cheatography.com/public/images/cheatography_logo.pdf}} } \end{tabulary} \columnbreak \begin{tabulary}{11cm}{L} \vspace{-2pt}\large{\bf{\textcolor{DarkBackground}{\textrm{CS107 Computer Organization and Systems Cheat Sheet}}}} \\ \normalsize{by \textcolor{DarkBackground}{yueqiao} via \textcolor{DarkBackground}{\uline{cheatography.com/167654/cs/35043/}}} \end{tabulary} \end{multicols}} \fancyfoot[L]{ \footnotesize \noindent \begin{multicols}{3} \begin{tabulary}{5.8cm}{LL} \SetRowColor{FootBackground} \mymulticolumn{2}{p{5.377cm}}{\bf\textcolor{white}{Cheatographer}} \\ \vspace{-2pt}yueqiao \\ \uline{cheatography.com/yueqiao} \\ \end{tabulary} \vfill \columnbreak \begin{tabulary}{5.8cm}{L} \SetRowColor{FootBackground} \mymulticolumn{1}{p{5.377cm}}{\bf\textcolor{white}{Cheat Sheet}} \\ \vspace{-2pt}Not Yet Published.\\ Updated 11th December, 2022.\\ Page {\thepage} of \pageref{LastPage}. \end{tabulary} \vfill \columnbreak \begin{tabulary}{5.8cm}{L} \SetRowColor{FootBackground} \mymulticolumn{1}{p{5.377cm}}{\bf\textcolor{white}{Sponsor}} \\ \SetRowColor{white} \vspace{-5pt} %\includegraphics[width=48px,height=48px]{dave.jpeg} Measure your website readability!\\ www.readability-score.com \end{tabulary} \end{multicols}} \begin{document} \raggedright \raggedcolumns % Set font size to small. Switch to any value % from this page to resize cheat sheet text: % www.emerson.emory.edu/services/latex/latex_169.html \footnotesize % Small font. \begin{multicols*}{3} \begin{tabularx}{5.377cm}{X} \SetRowColor{DarkBackground} \mymulticolumn{1}{x{5.377cm}}{\bf\textcolor{white}{Unix}} \tn % Row 0 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{Unix}}: a set of standards and tools commonly used in software development.} \tn % Row Count 2 (+ 2) % Row 1 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{The {\bf{command-line}} is a text-based interface (i.e., terminal interface) to navigate a computer, instead of a Graphical User Interface (GUI).} \tn % Row Count 5 (+ 3) \hhline{>{\arrayrulecolor{DarkBackground}}-} \end{tabularx} \par\addvspace{1.3em} \begin{tabularx}{5.377cm}{X} \SetRowColor{DarkBackground} \mymulticolumn{1}{x{5.377cm}}{\bf\textcolor{white}{Unix Commands}} \tn % Row 0 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{cd}} – change directories (..)} \tn % Row Count 1 (+ 1) % Row 1 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{{\bf{ls}} – list directory contents (-l, -a: hidden files)} \tn % Row Count 3 (+ 2) % Row 2 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{mkdir}} – make directory} \tn % Row Count 4 (+ 1) % Row 3 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{{\bf{emacs}} – open text editor} \tn % Row Count 5 (+ 1) % Row 4 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{rm}} – remove file or folder (-rf)} \tn % Row Count 6 (+ 1) % Row 5 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{{\bf{rmdir}} - remove empty dir} \tn % Row Count 7 (+ 1) % Row 6 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{man}} – view manual pages} \tn % Row Count 8 (+ 1) % Row 7 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{{\bf{tree cs107 -F}} (show files and directories in tree)} \tn % Row Count 10 (+ 2) % Row 8 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{pwd}} - output absolute path to current location} \tn % Row Count 11 (+ 1) % Row 9 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{{\bf{cp source dest}} - copy (-r to copy directory)} \tn % Row Count 12 (+ 1) % Row 10 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{mv}} - move (rename)} \tn % Row Count 13 (+ 1) % Row 11 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{{\bf{cat file1 (file2 file3)}} print file(s one after another)} \tn % Row Count 15 (+ 2) % Row 12 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{grep "binky(.*)" program.c}} - search text in files (. any char, * zero or more repeats of left char, \textasciicircum{} beginning of line, \$ end of line)} \tn % Row Count 18 (+ 3) % Row 13 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{{\bf{find assign1 -name "*.c"}} - search the assign1 folder for all .c files} \tn % Row Count 20 (+ 2) % Row 14 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{diff hello.c hello2.c}} - find the diff of two files} \tn % Row Count 22 (+ 2) % Row 15 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{{\bf{./hello \textgreater{} outputFile.txt}} - save output to file} \tn % Row Count 23 (+ 1) % Row 16 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{\textgreater{}\textgreater{}}} - append the output to an existing file} \tn % Row Count 24 (+ 1) % Row 17 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{{\bf{ diff file1.c file2.c | grep "\#include" | wc -l}} - pipe, find \# of diff lines that contain \#include for two files} \tn % Row Count 27 (+ 3) % Row 18 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{./addTwoNumbers \textless{} twoNumbers.txt}} - read user input from file} \tn % Row Count 29 (+ 2) \hhline{>{\arrayrulecolor{DarkBackground}}-} \end{tabularx} \par\addvspace{1.3em} \begin{tabularx}{5.377cm}{X} \SetRowColor{DarkBackground} \mymulticolumn{1}{x{5.377cm}}{\bf\textcolor{white}{Bits and Bytes}} \tn % Row 0 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{Two's Complement}}: binary digits inverted, plus 1} \tn % Row Count 2 (+ 2) % Row 1 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{{\bf{Overflow}}: Exceed max val-{}-\textgreater{}overflow back to smallest; below min val-{}-\textgreater{}overflow back to largest} \tn % Row Count 4 (+ 2) % Row 2 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{SCHAR\_MIN (-128), UCHAR\_MAX (255), SHRT\_MIN, INT\_MAX (2147483647), UINT\_MAX, ULONG\_MAX} \tn % Row Count 6 (+ 2) % Row 3 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{{\bf{Casting}}: Replicate bit, interpreted differently ({\emph{int v = -1; unsigned int uv = v;}}/ {\emph{(unsigned int) v}}/ -12345U)} \tn % Row Count 9 (+ 3) % Row 4 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{C will implicitly cast the signed argument to unsigned when comparing} \tn % Row Count 11 (+ 2) % Row 5 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{Max is 0 followed by all 1s, min is 1 followed by all 0s in signed} \tn % Row Count 13 (+ 2) % Row 6 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{Expanding bit representation: zero (unsigned) / sign extension (signed); promote to larger type for comparison} \tn % Row Count 16 (+ 3) % Row 7 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{Truncating bit representation: discard more significant bits} \tn % Row Count 18 (+ 2) % Row 8 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{bitwise operators}}: \&, |, \textasciitilde{}, \textasciicircum{}, \textless{}\textless{}, \textgreater{}\textgreater{}} \tn % Row Count 19 (+ 1) % Row 9 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{\textasciicircum{} with 1 to flip, with 0 to let a bit go through} \tn % Row Count 20 (+ 1) % Row 10 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{\textasciicircum{} flip isolated bits, \textasciitilde{} flip all bits} \tn % Row Count 21 (+ 1) % Row 11 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{num \& (num - 1): clears the lowest 1} \tn % Row Count 22 (+ 1) % Row 12 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{Right shift fills with sign bit (signed, arithmetic right shift); fills with 0s (unsigned, logical right shift)} \tn % Row Count 25 (+ 3) % Row 13 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{{\bf{long num = 1L \textless{}\textless{} 32;}}, CHAR\_BIT = 8} \tn % Row Count 26 (+ 1) % Row 14 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{int sign = value \textgreater{}\textgreater{} (sizeof(int) * CHAR\_BIT - 1); return (value \textasciicircum{} sign) - sign;} \tn % Row Count 28 (+ 2) \hhline{>{\arrayrulecolor{DarkBackground}}-} \end{tabularx} \par\addvspace{1.3em} \begin{tabularx}{5.377cm}{X} \SetRowColor{DarkBackground} \mymulticolumn{1}{x{5.377cm}}{\bf\textcolor{white}{Characters and C Strings}} \tn % Row 0 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{char: single character / "glyph" ('\textbackslash{}\textbackslash{}', '\textbackslash{}n', 'A' (65)), represented as int (ASCII), lowercase 32 more than upper} \tn % Row Count 3 (+ 3) % Row 1 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{isalpha(ch) (alphabet), islower, isupper, isspace (space, \textbackslash{}t, \textbackslash{}n...), isdigit, toupper, tolower (return char, not modify existing)} \tn % Row Count 6 (+ 3) % Row 2 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{C Strings: array of chars with '\textbackslash{}0', null-terminating character, pass char* as param (add. of 1st char), str == \&str{[}0{]}} \tn % Row Count 9 (+ 3) % Row 3 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{int foo(char *str) == int foo(char str{[}{]}), str-pointer (char** argv == char* argv{[}{]}, double pointer)} \tn % Row Count 12 (+ 3) \hhline{>{\arrayrulecolor{DarkBackground}}-} \end{tabularx} \par\addvspace{1.3em} \begin{tabularx}{5.377cm}{X} \SetRowColor{DarkBackground} \mymulticolumn{1}{x{5.377cm}}{\bf\textcolor{white}{Pointers and Arrays}} \tn % Row 0 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{Pointer}}: A variable that stores a memory address} \tn % Row Count 2 (+ 2) % Row 1 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{{\bf{Memory}}: A big array of bytes; each byte unique numeric index (generally written in hex)} \tn % Row Count 4 (+ 2) % Row 2 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{*}}: declaration-pointer, \seqsplit{operation-dereference/value} at address} \tn % Row Count 6 (+ 2) % Row 3 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{Pass value as param, C passes a copy of the value; take add (ptr) as a param, go to add when need val} \tn % Row Count 9 (+ 3) % Row 4 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{char* could also ptr to {\bf{single char}}} \tn % Row Count 10 (+ 1) % Row 5 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{create strings as char{[}{]}, pass them around as char *} \tn % Row Count 12 (+ 2) % Row 6 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{Avoid \&str when str is char{[}{]}! str/\&str{[}0{]}} \tn % Row Count 13 (+ 1) % Row 7 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{\&arr does nothing on arrays, but \&ptr on pointers gets its address} \tn % Row Count 15 (+ 2) % Row 8 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{sizeof(arr) gets the size of an array in bytes, but sizeof(ptr) is always 8} \tn % Row Count 17 (+ 2) % Row 9 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{An array variable refers to an entire block of memory. {\bf{Cannot}} reassign an existing array to be equal to a new array.} \tn % Row Count 20 (+ 3) % Row 10 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{Pass an array as param, C makes copy of add. of 1st element and pass a ptr to function (No sizeof with param!!)} \tn % Row Count 23 (+ 3) \hhline{>{\arrayrulecolor{DarkBackground}}-} \end{tabularx} \par\addvspace{1.3em} \begin{tabularx}{5.377cm}{X} \SetRowColor{DarkBackground} \mymulticolumn{1}{x{5.377cm}}{\bf\textcolor{white}{Stack Memory and Heap Memory}} \tn % Row 0 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{The {\bf{stack}} is the place where all local variables and parameters live for each function. Goes downwards when func called and shrinks upwards when func finished} \tn % Row Count 4 (+ 4) % Row 1 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{The {\bf{heap}} is a part of memory below the stack. Only goes away when free. Grows upward. Dynamic memory during program runtime.} \tn % Row Count 7 (+ 3) % Row 2 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{Allocate with {\bf{malloc/realloc/strdup/calloc}}, e.g. int *arr = \seqsplit{malloc(sizeof(int)*len));} assert(arr != NULL); free(arr);} \tn % Row Count 10 (+ 3) % Row 3 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{int *scores = calloc(n\_elem, sizeof(int)); (zeros out memory); char* str = strdup("Hello"); malloc + strcpy} \tn % Row Count 13 (+ 3) % Row 4 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{CANNOT free part of previous alloc, MUST free add received in alloc} \tn % Row Count 15 (+ 2) % Row 5 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{A {\bf{memory leak}} is when you do not free memory you previously allocated.} \tn % Row Count 17 (+ 2) % Row 6 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{char *str = strdup("Hello"); str = realloc(str, new\_len + 1); (Must be ptrs returned by malloc, etc.), automatic free of prev smaller one} \tn % Row Count 20 (+ 3) \hhline{>{\arrayrulecolor{DarkBackground}}-} \end{tabularx} \par\addvspace{1.3em} \begin{tabularx}{5.377cm}{X} \SetRowColor{DarkBackground} \mymulticolumn{1}{x{5.377cm}}{\bf\textcolor{white}{Generics}} \tn % Row 0 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{void*}}: any pointer, No dereferencing/Pointer Arithmetic (cast to char* to do pointer arithmetic)} \tn % Row Count 3 (+ 3) % Row 1 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{{\bf{memcpy}} is a function that copies a specified amount of bytes at one address to another address (returns dest).} \tn % Row Count 6 (+ 3) % Row 2 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{memmove}} handles overlapping memory figures (returns dest)} \tn % Row Count 8 (+ 2) % Row 3 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{Function pointers: {[}return type{]} (*{[}name{]})({[}parameters{]}) ("callback" function, function writer vs function caller)} \tn % Row Count 11 (+ 3) % Row 4 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{qsort: sort arr of any type; bsearch: binary search to search for a key in arr any type; lfind: linear search to search for key (return NULL not found); lsearch: linear search, add key if not found} \tn % Row Count 15 (+ 4) \hhline{>{\arrayrulecolor{DarkBackground}}-} \end{tabularx} \par\addvspace{1.3em} \begin{tabularx}{5.377cm}{X} \SetRowColor{DarkBackground} \mymulticolumn{1}{x{5.377cm}}{\bf\textcolor{white}{GDB}} \tn % Row 0 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\emph{GDB}}: p/x num (hex), p/d num (digit), p/t num (binary), p/c num (char), p/u (unsigned decimal); p nums{[}1{]}@2 (start at nums{[}1{]} print 2)} \tn % Row Count 3 (+ 3) % Row 1 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{gdb myprogram; b main; r 82 (run with arts); n, s, continue (next,step into, continue); info (args, locals)} \tn % Row Count 6 (+ 3) % Row 2 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{ctrl-c + {\bf{backtrace}} - display the current call stack, meaning what functions are currently executing.} \tn % Row Count 9 (+ 3) \hhline{>{\arrayrulecolor{DarkBackground}}-} \end{tabularx} \par\addvspace{1.3em} \begin{tabularx}{5.377cm}{X} \SetRowColor{DarkBackground} \mymulticolumn{1}{x{5.377cm}}{\bf\textcolor{white}{Optimizationn}} \tn % Row 0 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{Optimization: task of making program faster/more efficient with space or time} \tn % Row Count 2 (+ 2) % Row 1 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{gcc -O0 (mostly literal translation), O2 (enable nearly all reasonable optimizations), O3 (more aggressive, trade size for speed), Os (optimize for size), -Ofast (disregard standards compliance)} \tn % Row Count 6 (+ 4) % Row 2 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{Target: static instruction count, dynamic, cycle count/execution time} \tn % Row Count 8 (+ 2) % Row 3 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{Constant Folding pre-calculates constants at compile-time where possible.} \tn % Row Count 10 (+ 2) % Row 4 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{Common Sub-Expression Elimination prevents the recalculation of the same thing many times by doing it once and saving the result.} \tn % Row Count 13 (+ 3) % Row 5 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{Dead code elimination removes code that doesn't serve a purpose (empty for loop, if/else same operation)} \tn % Row Count 16 (+ 3) % Row 6 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{Strength reduction changes divide to multiply, multiply to add/shift, and mod to AND to avoid using instructions that cost many cycles (multiply and divide)} \tn % Row Count 20 (+ 4) % Row 7 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{Code motion moves code outside of a loop if possible.} \tn % Row Count 22 (+ 2) % Row 8 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{Tail recursion is an example of where GCC can identify recursive patterns that can be more efficiently implemented iteratively.} \tn % Row Count 25 (+ 3) % Row 9 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{Loop unrolling: Do n loop iterations' worth of work per actual loop iteration, so we save ourselves from doing the loop overhead (test and jump) every time, and instead incur overhead only every n-th time.} \tn % Row Count 30 (+ 5) \hhline{>{\arrayrulecolor{DarkBackground}}-} \end{tabularx} \par\addvspace{1.3em} \begin{tabularx}{5.377cm}{X} \SetRowColor{DarkBackground} \mymulticolumn{1}{x{5.377cm}}{\bf\textcolor{white}{Heap Allocator}} \tn % Row 0 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{A heap allocator is a suite of functions that cooperatively fulfill requests for dynamically allocated memory.} \tn % Row Count 3 (+ 3) % Row 1 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{When initialized, a heap allocator tracks the base addr and size of a large contiguous block of memory: heap.} \tn % Row Count 6 (+ 3) % Row 2 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{Throughput: \# requests completed per unit time (minimizing avg time to satisfy a request) vs Utilization: how efficiently we make use of the limited heap memory to satisfy requests.} \tn % Row Count 10 (+ 4) % Row 3 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{Utilization: largest addr used as low as possible} \tn % Row Count 11 (+ 1) % Row 4 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{Internal Fragmentation: allocated block larger than what's needed, external fragmentation; no single block large enough to satisfy allocation request, even though enough aggregate free memory available} \tn % Row Count 16 (+ 5) % Row 5 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{Implicit free list allocator: 8 byte (or larger) header, by storing header info, implicitly maintaining a list of free blocks (malloc linear in total number of blocks)} \tn % Row Count 20 (+ 4) % Row 6 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{Explicit free list allocator: stores ptrs to next and previous free block inside each free block's payload (look just the free blocks on linked list for malloc, linear in \# free blocks, update linked list when free), throughput increase, costs: design and internal fragmentation} \tn % Row Count 26 (+ 6) \hhline{>{\arrayrulecolor{DarkBackground}}-} \end{tabularx} \par\addvspace{1.3em} \begin{tabularx}{5.377cm}{X} \SetRowColor{DarkBackground} \mymulticolumn{1}{x{5.377cm}}{\bf\textcolor{white}{Assembly: Control Flow \& Function Call}} \tn % Row 0 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{\%rip}} stores addr of next instruction to execute (\%rip += size of bytes of curr instruction)} \tn % Row Count 2 (+ 2) % Row 1 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{direct jump: jum Label, {\emph{indirect jump}}: jmp *\%rax (jump to instruction at addr in \%rax)} \tn % Row Count 4 (+ 2) % Row 2 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{Condition code}} regs store info about most recent arithmetic/logical operation ({\bf{lea}} NOT update; logical like xor set CF \& OF to 0; shift set CF to last bit shifted out and OF to 0; inc and dec set OF and ZF, leave CF unchanged)} \tn % Row Count 9 (+ 5) % Row 3 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{CF: unsigned overflow, OF: two's-complement overflow/underflow} \tn % Row Count 11 (+ 2) % Row 4 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{test}} and {\bf{cmp}} just set condition codes (not store result)} \tn % Row Count 13 (+ 2) % Row 5 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{{\bf{static instruction count}}: \# of written instructions; {\bf{dynamic instruction count}}: \# of executed instructions when program is run} \tn % Row Count 16 (+ 3) % Row 6 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{\%rsp}}: stores addr of "top" of stack, must point to same place before func called and after returned} \tn % Row Count 19 (+ 3) % Row 7 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{push: R{[}\%rsp{]}\textless{}-R{[}\%rsp{]} - 8; pop+8} \tn % Row Count 20 (+ 1) % Row 8 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{call}}: push next value of \%rip onto stack, set \%rip point to beginning of specified function's instructions} \tn % Row Count 23 (+ 3) % Row 9 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{{\bf{ret}}: pops instruction addr from stack and stores it in \%rip} \tn % Row Count 25 (+ 2) % Row 10 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{stored \%rip: {\bf{return address}}, addr of instruction where execution would have continued had flow not been interrupted by function call} \tn % Row Count 28 (+ 3) % Row 11 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{{\bf{nop}}: no-op, do nothing (make functions align); mov \%ebx,\%ebx, zeros out top 32 bits; xor \%ebx,\%ebx, set to 0, optmizes for performances \& code size} \tn % Row Count 32 (+ 4) \end{tabularx} \par\addvspace{1.3em} \vfill \columnbreak \begin{tabularx}{5.377cm}{X} \SetRowColor{DarkBackground} \mymulticolumn{1}{x{5.377cm}}{\bf\textcolor{white}{Assembly: Control Flow \& Function Call (cont)}} \tn % Row 12 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{Suppose \%rcx stores arr{[}1{]} addr, to get arr{[}0{]} value: p *((int*)\$rcx-1)} \tn % Row Count 2 (+ 2) \hhline{>{\arrayrulecolor{DarkBackground}}-} \end{tabularx} \par\addvspace{1.3em} \begin{tabularx}{5.377cm}{X} \SetRowColor{DarkBackground} \mymulticolumn{1}{x{5.377cm}}{\bf\textcolor{white}{Assembly: Arithmetic and Logic}} \tn % Row 0 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{Machine code 1s and 0s, human-readable form assembly (GCC compiler)} \tn % Row Count 2 (+ 2) % Row 1 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{Sequential instructions sequential in memory} \tn % Row Count 3 (+ 1) % Row 2 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{Instruction operation name "opcode" (mov, add, etc.), "operands" (arguments, max 2)} \tn % Row Count 5 (+ 2) % Row 3 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{\${[}number{]} constant value, "immediate"; \%{[}name{]} register} \tn % Row Count 7 (+ 2) % Row 4 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{Register: fast read/write memory slot right on CPU that can hold variable values (not in memory, 64-bit space inside processor, total 16)} \tn % Row Count 10 (+ 3) % Row 5 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{mov: \$ only src, \% both, memory location at least one (copy value at addr)} \tn % Row Count 12 (+ 2) % Row 6 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{Indirect(): dereferencing, (\%rbx) copy value at addr stored in \%rbx} \tn % Row Count 14 (+ 2) % Row 7 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{\%rip: addr of next instruction to execute} \tn % Row Count 15 (+ 1) % Row 8 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{\%rsp: addr of current top of stack} \tn % Row Count 16 (+ 1) % Row 9 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{{\bf{movl}} writing to reg also set high order 4 bytes to 0} \tn % Row Count 18 (+ 2) % Row 10 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{movabsq}} 64-bit immediate, movq only 32-bit. 64-bit imm src, only reg as dest} \tn % Row Count 20 (+ 2) % Row 11 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{movz, movs, smaller src larger dst, src: memory/reg, dest: reg} \tn % Row Count 22 (+ 2) % Row 12 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{cltq}}: sign-extend \%eax to \%rax} \tn % Row Count 23 (+ 1) % Row 13 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{parentheses require regs in par. be 64-bit} \tn % Row Count 24 (+ 1) % Row 14 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{mov}} copies data {\bf{at}} addr, {\bf{lea}} copies value of src (addr) {\bf{itself}} (only lea not dereferencing)} \tn % Row Count 27 (+ 3) % Row 15 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{{\bf{inc D}} D\textless{}-D + 1, {\bf{dec D}} D \textless{}- D-1} \tn % Row Count 28 (+ 1) % Row 16 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{shift k, D, k only \%cl (w bits data, looks at lower-order {\bf{log2(w)}} bits of \%cl to know how much to shift) or imm} \tn % Row Count 31 (+ 3) \end{tabularx} \par\addvspace{1.3em} \vfill \columnbreak \begin{tabularx}{5.377cm}{X} \SetRowColor{DarkBackground} \mymulticolumn{1}{x{5.377cm}}{\bf\textcolor{white}{Assembly: Arithmetic and Logic (cont)}} \tn % Row 17 \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{{\bf{imul}}: two operands, multiplies and truncates to fit in the second; one operand, multiplies by \%rax, higher-order 64 bits in \%rdx, lower in \%rax} \tn % Row Count 3 (+ 3) % Row 18 \SetRowColor{white} \mymulticolumn{1}{x{5.377cm}}{{\bf{idivq}}: divide 128-bit by 64-bit, higher-order 64 bit of dividend stored in \%rdx, lower order \%rax, only list divisor as operand (quotient \%rax, remainder \%rdx, {\bf{cqto}} sign-extends 64-bit dividend)} \tn % Row Count 8 (+ 5) \hhline{>{\arrayrulecolor{DarkBackground}}-} \end{tabularx} \par\addvspace{1.3em} \begin{tabularx}{5.377cm}{X} \SetRowColor{DarkBackground} \mymulticolumn{1}{x{5.377cm}}{\bf\textcolor{white}{C Program Example}} \tn \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{\#define CONSTANT 0x8 \newline int main(int argc, char {\emph{argv{[}{]}) \{ \newline char }}prefix = "CS"; \newline int number = 107; \newline // \%s (string), \%d (integer), \%f (double) \newline printf("You are in \%s\%d\textbackslash{}n", prefix, number); \newline return 0; \newline \}} \tn \hhline{>{\arrayrulecolor{DarkBackground}}-} \end{tabularx} \par\addvspace{1.3em} \begin{tabularx}{5.377cm}{X} \SetRowColor{DarkBackground} \mymulticolumn{1}{x{5.377cm}}{\bf\textcolor{white}{Assignment 0}} \tn \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{/{\emph{ Unix \newline ls \seqsplit{samples/server\_files/home/} \textgreater{}\textgreater{} home\_dir.txt \newline diff \seqsplit{samples/server\_files/users}.list home\_dir.txt \newline grep "sudo" \seqsplit{samples/server\_files/home/mattv/}.bash\_history }}/ \newline int main(int argc, char {\emph{argv{[}{]}) \{ \newline int nlevels = DEFAULT\_LEVELS; \newline if (argc \textgreater{} 1) \{ \newline nlevels = atoi(argv{[}1{]}); \newline if (nlevels \textless{} 0 || nlevels \textgreater{} 8) \{ \newline // void error(int status, int errnum, const char }}format, ...); \newline error(1, 0, "out of range"); \newline \} \newline \} \newline \seqsplit{print\_triangle(nlevels);} \newline return 0; \newline \}} \tn \hhline{>{\arrayrulecolor{DarkBackground}}-} \end{tabularx} \par\addvspace{1.3em} \begin{tabularx}{5.377cm}{X} \SetRowColor{DarkBackground} \mymulticolumn{1}{x{5.377cm}}{\bf\textcolor{white}{Assignment 1}} \tn \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{long signed\_max(int bitwidth) \{ \newline return \textasciitilde{}signed\_min(bitwidth); \newline \} \newline long signed\_min(int bitwidth) \{ \newline return -1L \textless{}\textless{} (bitwidth - 1); \newline \} \newline long sat\_add(long operand1, long operand2, int bitwidth) \{ \newline if (!((operand1 \textgreater{}\textgreater{} (bitwidth - 1)) \& 1L) \&\& \newline !((operand2 \textgreater{}\textgreater{} (bitwidth - 1)) \& 1L) \&\& \newline (((operand1 + operand2) \textgreater{}\textgreater{} (bitwidth - 1)) \& 1L)) \{ \newline return signed\_max(bitwidth); \newline \} \newline if (((operand1 \textgreater{}\textgreater{} (bitwidth - 1)) \& 1L) \&\& \newline ((operand2 \textgreater{}\textgreater{} (bitwidth - 1)) \& 1L) \&\& \newline !(((operand1 + operand2) \textgreater{}\textgreater{} (bitwidth - 1)) \& 1L)) \{ \newline return signed\_min(bitwidth); \newline \} \newline return operand1 + operand2; \newline \} \newline int to\_utf8(unsigned short code\_point, unsigned char utf8\_bytes{[}{]}) \{ \newline if (code\_point \textless{}= 0x7f) \{ \newline utf8\_bytes{[}0{]} = code\_point; \newline return 1; \newline \} else if (code\_point \textless{}= 0x7ff) \{ \newline utf8\_bytes{[}0{]} = 0xc0; // represents 11000000. \newline utf8\_bytes{[}1{]} = 0x80; // represents 10000000. \newline utf8\_bytes{[}0{]} |= (code\_point \& 0x7c0) \textgreater{}\textgreater{} 6; // 0x7c0 provides the bit mask 11100000. \newline utf8\_bytes{[}1{]} |= code\_point \& 0x3f; // 0x3f provides the bit mask 00111111. \newline \newline return 2; \newline \} else \{ \newline utf8\_bytes{[}0{]} = 0xe0; // represents 11100000. \newline utf8\_bytes{[}1{]} = 0x80; // represents 10000000. \newline utf8\_bytes{[}2{]} = 0x80; // represents 10000000. \newline utf8\_bytes{[}0{]} |= (code\_point \& 0xf000) \textgreater{}\textgreater{} 12; // 0xf000 provides the bit mask 1111000000000000. \newline utf8\_bytes{[}1{]} |= (code\_point \& 0xfc0) \textgreater{}\textgreater{} 6; // 0xfc0 provides the bit mask 0000111111000000. \newline utf8\_bytes{[}2{]} |= code\_point \& 0x3f; // 0x3f provides the bit mask 0000000000111111. \newline return 3; \newline \} \newline \} \newline \#define BIT\_MASK\_3 7L \newline unsigned long advance(unsigned long cur\_gen, unsigned char ruleset) \{ \newline unsigned long next\_gen = 0; \newline unsigned long neighborhood = 0; \newline neighborhood = (cur\_gen \textless{}\textless{} 1) \& BIT\_MASK\_3; \newline next\_gen |= (ruleset \textgreater{}\textgreater{} neighborhood) \& 1L; \newline \newline for (int i = 0; i \textless{}= sizeof(long) {\emph{ CHAR\_BIT - 2; ++i) \{ \newline neighborhood = (cur\_gen \textgreater{}\textgreater{} i) \& BIT\_MASK\_3; \newline next\_gen |= ((ruleset \textgreater{}\textgreater{} neighborhood) \& 1L) \textless{}\textless{} (i + 1); \newline \} \newline return next\_gen; \newline \} \newline \newline void \seqsplit{draw\_generation(unsigned} long gen) \{ \newline for (int i = sizeof(long) }} CHAR\_BIT - 1; i \textgreater{}= 0; -{}-i) \{ \newline if ((gen \textgreater{}\textgreater{} i) \& 1L) \{ \newline printf(LIVE\_STR); \newline \} else \{ \newline printf(EMPTY\_STR); \newline \} \newline \} \newline printf("\textbackslash{}n"); \newline \}} \tn \hhline{>{\arrayrulecolor{DarkBackground}}-} \end{tabularx} \par\addvspace{1.3em} \begin{tabularx}{5.377cm}{X} \SetRowColor{DarkBackground} \mymulticolumn{1}{x{5.377cm}}{\bf\textcolor{white}{Assignment 2}} \tn \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{const char *get\_env\_value(const char {\emph{envp{[}{]}, const char }}key) \{ \newline int lenKey = strlen(key); \newline for (int i = 0; envp{[}i{]} != NULL; ++i) \{ \newline char{\emph{ match = strstr(envp{[}i{]}, key); \newline if (match == envp{[}i{]} \&\& }}(match + lenKey) == '=') \{ \newline return match + lenKey + 1; \newline \} \newline \} \newline return NULL; \newline \} \newline \newline bool scan\_token(const char {\emph{*p\_input, \newline const char }}delimiters, char buf{[}{]}, size\_t buflen) \{ \newline const char{\emph{ begin = }}p\_input; \newline begin += strspn(begin, delimiters); \newline const char{\emph{ end = begin + strcspn(begin, delimiters); \newline \newline int maxlen = 0; \newline if (end - begin \textless{}= buflen - 1) \{ \newline maxlen = end - begin; \newline \} else \{ \newline maxlen = buflen - 1; \newline \} \newline if (maxlen \textless{}= 0) \{ \newline }}p\_input = begin; \newline return false; \newline \} \newline strncpy(buf, begin, maxlen); \newline buf{[}maxlen{]} = '\textbackslash{}0'; \newline {\emph{p\_input = begin + maxlen; \newline return true; \newline \} \newline int main(int argc, char }}argv{[}{]}, const char {\emph{envp{[}{]}) \{ \newline const char }}searchpath = get\_env\_value(envp, "MYPATH"); \newline if (searchpath == NULL) \{ \newline searchpath = get\_env\_value(envp, "PATH"); \newline \} \newline if (argc == 1) \{ \newline char dir{[}PATH\_MAX{]}; \newline const char {\emph{remaining = searchpath; \newline \newline printf("Directories in search path:\textbackslash{}n"); \newline while (scan\_token(\&remaining, ":", dir, sizeof(dir))) \{ \newline printf("\%s\textbackslash{}n", dir); \newline \} \newline \} else \{ \newline for (size\_t i = 1; i \textless{} argc; ++i) \{ \newline const char }}executable = argv{[}i{]}; \newline char dir{[}PATH\_MAX{]}; \newline const char *remaining = searchpath; \newline while (scan\_token(\&remaining, ":", dir, sizeof(dir))) \{ \newline strcat(dir, "/"); \newline strcat(dir, executable); \newline if (access(dir, R\_OK | X\_OK) == 0) \{ \newline printf("\%s\textbackslash{}n", dir); \newline break; \newline \} \newline \} \newline \} \newline \} \newline return 0; \newline \}} \tn \hhline{>{\arrayrulecolor{DarkBackground}}-} \end{tabularx} \par\addvspace{1.3em} \begin{tabularx}{5.377cm}{X} \SetRowColor{DarkBackground} \mymulticolumn{1}{x{5.377cm}}{\bf\textcolor{white}{Assignment 3}} \tn \SetRowColor{LightBackground} \mymulticolumn{1}{x{5.377cm}}{char *read\_line(FILE {\emph{file\_pointer) \{ \newline char}} buffer = malloc(MINIMUM\_SIZE); \newline assert(buffer != NULL); \newline size\_t curSize = MINIMUM\_SIZE; \newline char{\emph{ curPtr = fgets(buffer, curSize, file\_pointer); \newline if (curPtr == NULL) \{ \newline free(buffer); \newline return NULL; \newline \} \newline size\_t strLen = strlen(buffer); \newline while (}}(buffer + strLen - 1) != '\textbackslash{}n') \{ \newline curSize {\emph{= 2; \newline buffer = realloc(buffer, curSize); \newline assert(buffer != NULL); \newline curPtr = buffer + strLen; \newline char}} newPtr = fgets(curPtr, curSize - strLen, file\_pointer); \newline if (newPtr == NULL) \{ \newline {\emph{curPtr = '\textbackslash{}0'; \newline break; \newline \} else \{ \newline curPtr = newPtr; \newline \} \newline strLen += strlen(curPtr); \newline \} \newline if (}}(buffer + strLen - 1) == '\textbackslash{}n') \{ \newline {\emph{(buffer + strLen - 1) = '\textbackslash{}0'; \newline \} \newline return buffer; \newline \} \newline void print\_last\_n(FILE }}file\_pointer, int n) \{ \newline char{\emph{ lines{[}n{]}; \newline char}} line = NULL; \newline int idx = 0; \newline size\_t cnt\_read = 0; \newline while ((line = \seqsplit{read\_line(file\_pointer))} != NULL) \{ \newline lines{[}idx{]} = line; \newline idx = (idx + 1) \% n; \newline ++cnt\_read; \newline \} \newline if (cnt\_read \textless{} n) \{ \newline idx = 0; \newline \} else \{ \newline cnt\_read = n; \newline \} \newline line = lines{[}idx{]}; \newline size\_t cnt\_print = 0; \newline while (cnt\_print \textless{} cnt\_read) \{ \newline printf("\%s\textbackslash{}n", line); \newline free(line); \newline idx = (idx + 1) \% n; \newline line = lines{[}idx{]}; \newline ++cnt\_print; \newline \} \newline \} \newline struct Element \{ \newline char{\emph{ str; \newline int cnt; \newline \}; \newline \newline void print\_uniq\_lines(FILE }}file\_pointer) \{ \newline size\_t curSize = ESTIMATE; \newline struct Element{\emph{ arr = malloc(sizeof(struct Element) }} curSize); \newline assert(arr != NULL); \newline size\_t cntElement = 0; \newline char{\emph{ line = NULL; \newline while ((line = \seqsplit{read\_line(file\_pointer))} != NULL) \{ \newline bool found = false; \newline for (size\_t i = 0; i \textless{} cntElement; ++i) \{ \newline if (strcmp(line, arr{[}i{]}.str) == 0) \{ \newline ++arr{[}i{]}.cnt; \newline found = true; \newline free(line); \newline break; \newline \} \newline \} \newline if (!found) \{ \newline arr{[}cntElement{]}.str = line; \newline arr{[}cntElement{]}.cnt = 1; \newline ++cntElement; \newline if (cntElement == curSize) \{ \newline curSize += ESTIMATE; \newline arr = realloc(arr, sizeof(struct Element) }} curSize); \newline assert(arr != NULL); \newline \} \newline \} \newline \} \newline for (size\_t i = 0; i \textless{} cntElement; ++i) \{ \newline printf("\%7d \%s\textbackslash{}n", arr{[}i{]}.cnt, arr{[}i{]}.str); \newline free(arr{[}i{]}.str); \newline \} \newline free(arr); \newline \}} \tn \hhline{>{\arrayrulecolor{DarkBackground}}-} \end{tabularx} \par\addvspace{1.3em} % That's all folks \end{multicols*} \end{document}