<http://www.w3.org/2009/08/skos-reference/skos.html#note>
"software modularity group  Programming: Poetry, Gears or Magic? Gregor Kiczales NSERC, Xerox, Sierra Systems Software Design Chair Professor of Computer Science University of British Columbia  \u000Csubject of the talk programming and programming languages (PL) \u2022 use demands of current software systems \u2022 to look at 4 generations of PL research \u2013 problems addressed \u2013 core idea \u2013 what we learned about building programs  \u2022 look at some (fairly) real code \u2013 don\u2019t worry! you will be able to read this code \u2013 idealized but substantive  2/17/01 Vancouver Institute  2  UBC software modularity group  \u000Cthemes to explore \u2022 \u2022 \u2022 \u2022  what is code? what are \u201Clines of code\u201D? why is programming so interesting? so hard? why is software so fragile? what is the nature of the research? what questions do we ask? \u2022 what might happen in the future? \u2022 how can a program be beautiful or elegant \u2022 technical and esthetic principles of the field  2/17/01 Vancouver Institute  3  UBC software modularity group  \u000Ccurrent applications  2/17/01 Vancouver Institute  4  UBC software modularity group  \u000Ccurrent applications  2/17/01 Vancouver Institute  5  UBC software modularity group  \u000Ccurrent applications  2/17/01 Vancouver Institute  6  UBC software modularity group  \u000Ca \u2018simple\u2019 browser application  2/17/01 Vancouver Institute  7  UBC software modularity group  \u000Ca \u2018simple\u2019 browser application  2/17/01 Vancouver Institute  8  UBC software modularity group  \u000Ca very simple application print numbers from 1 to 3 1 2 3  2/17/01 Vancouver Institute  9  UBC software modularity group  \u000Cdifferent scales  10 lines 1 2 3  2/17/01 Vancouver Institute  6  4  10 lines  10  10 lines  UBC software modularity group  \u000CPart I \u2013 starting small doing something 3 times before we can do this we surely need to be able to do this  1 2 3  \u2026 write a program to print 1 2 3 using ~1964 technology 2/17/01 Vancouver Institute  11  UBC software modularity group  \u000Cwho\u2019s on first? A:  B:  \u2022 \u2022 \u2022 \u2022  i = 1 if i &lt; 4 then goto B else goto C print(i) i = i + 1 goto A  \u2018goto\u2019 jumps to that label goto B, goto C, goto A what are A, B, C? what do they do?  C:  2/17/01 Vancouver Institute  12  UBC software modularity group  \u000Cover, back, and all around \u2022 test, body and end \u2022 but\u2026  i = 1 TEST: if i &lt; 4 then goto BODY else goto END  \u2013 \u2013 \u2013 \u2013  BODY: print(i) i = i + 1 goto TEST END:  2/17/01 Vancouver Institute  13  what happens when? first i is 1 how can it not be &lt; 4 ? what is this braid doing?  UBC software modularity group  \u000Celegant coding style \u2022 really one simple loop  i = 1 LOOP: print(i) i = i + 1 if i &lt; 4 then goto LOOP  \u2013 no \u201Ccrossing gotos\u201D \u2013 clear tag names  \u2022 this is \u201Celegant\u201D code \u2013 \u2013 \u2013 \u2013  concise nicely named reflects the structure idiomatic  2/17/01 Vancouver Institute  14  UBC software modularity group  \u000CPL support \u2022 eliminate goto \u2022 add explicit while loop  i = 1 while (i &lt; 4) { print(i) i = i + 1 }  \u2013 test and time of test \u2013 body { \u2026 }  \u2022 PL designer makes the rules \u2013 new words, new grammar  \u2022 you will write elegant code \u2013 don\u2019t use words like \u201Cgoto\u201D \u2013 say while when you \u201Cmean it\u201D  (actually, we can only encourage good style) 2/17/01 Vancouver Institute  15  UBC software modularity group  \u000C\u201Cstructured programming\u201D \u2022 a \u2018spirited\u2019 debate - Dijkstra, E. \u201CGOTO Statement Considered Harmful\u201D - Wulf, W. A. \u201CA Case Against the GOTO\u201D - Knuth, D. \u201CStructured Programming with goto Statements\u201D  1968 1972 1974  - Rubin, F. \u201C \u2018GOTO Considered Harmful\u2019 Considered Harmful\u201D 1987 \u2022 letter to editor of CACM asserts goto-less programming has cost businesses \"hundreds of millions of dollars\" \u2022 generated more response by far than any other issue ever considered in pages of the CACM  \u2022 many principles of the field forged during this time  2/17/01 Vancouver Institute  16  UBC software modularity group  \u000Cother options  you can still get a good fight over which of these is best  i = 1 while (i &lt; 4) { print(i) i = i + 1 }  some argue that writing \u201Ci not equal to 4\u201D more clearly expresses when the loop ends  i = 1 while (i != 4) { print(i) i = i + 1 }  2/17/01 Vancouver Institute  17  UBC software modularity group  \u000Cother options  you can still get a good fight over which of these is best i = 1 do { print(i) i = i + 1 } until (i = 3)  test at end makes end condition more clear  do (i = 1, i &lt; 4, i++) { print(i) }  general-purpose but still clearly a loop  dotimes (i 3) { print(i) }  most clear many argue too special-purpose  2/17/01 Vancouver Institute  18  UBC software modularity group  \u000Cwhy does this matter? \u2022 to the computer? \u2013 it doesn\u2019t, issues like this don\u2019t confuse the computer!  \u2022 but, ~10x maintenance vs. original development \u2022 programs always change \u2013 debug \u2013 add new functionality \u2013 integrate with new systems  \u2022 programs must be readable by others \u2013 have to tell a story \u2013 have a coherent structure \u2013 focus on the key points  2/17/01 Vancouver Institute  programs must be well-written  19  UBC software modularity group  \u000C\u201Cstructured programming\u201D \u2022 peak of research ~ 64 \u2013 75 \u2022 structured control mechanisms \u2013 \u2013 \u2013 \u2013 \u2013  eliminate \u2018goto\u2019 add explicit loops: do, while add explicit tests: if (&lt;test&gt;) then { \u2026 } else { \u2026 }, case\u2026 \u0002 prohibit non-standard control structures \u0002 \u2018encourages good style, use of idioms\u2019  \u2022 code is easier to understand \u2013 \u0002 easier to write, easier to read, easier to debug  \u2022 abstraction: a \u2018while loop\u2019 vs. details of looping \u2013 \u0002 100 lines of code felt like 10  2/17/01 Vancouver Institute  20  UBC software modularity group  \u000CPart II \u2013 a simple application \u2022 an image browser \u2013 3 choice menu \u2013 display image  \u2026 implement this simple image browser using structured programming 2/17/01 Vancouver Institute  21  UBC software modularity group  \u000Csimplified implementation main () { draw_label(\u201CHaida Browser\u201D); m = radio_menu( {\u201CWhale\u201D, \u201CEagle\u201D, \u201CDogfish\u201D}); q = button_menu({\u201CQuit\u201D}); while ( ! check_buttons(q) ) { n = check_buttons(m); draw_image(n); } }  2/17/01 Vancouver Institute  22  UBC software modularity group  \u000Csimplified implementation main () { draw_label(\u201CHaida Art Browser\u201D); m = radio_menu( {\u201CWhale\u201D, \u201CEagle\u201D, \u201CDogfish\u201D}); q = button_menu({\u201CQuit\u201D}); while ( ! check_buttons(q) ) { n = check_buttons(m); draw_image(n); } } draw_label (string) { w = calculate_width(string); print(string, WINDOW_PORT); set_x(get_x() + w); }  2/17/01 Vancouver Institute  23  UBC software modularity group  \u000Csimplified implementation main () { draw_label(\u201CHaida Art Browser\u201D); m = radio_menu( {\u201CWhale\u201D, \u201CEagle\u201D, \u201CDogfish\u201D}); q = button_menu({\u201CQuit\u201D}); while ( ! check_buttons(q) ) { n = check_buttons(m); draw_image(n); } } draw_label (string) { w = calculate_width(string); print(string, WINDOW_PORT); set_x(get_x() + w); } radio_menu(labels) { i = 0; while (i &lt; labels.size) { radio_button(i); draw_label(labels[i]); set_y(get_y() + RADIO_BUTTON_H); i++; } } 2/17/01 Vancouver Institute  24  UBC software modularity group  \u000Csimplified implementation main () { draw_label(\u201CHaida Art Browser\u201D); m = radio_menu( {\u201CWhale\u201D, \u201CEagle\u201D, \u201CDogfish\u201D}); q = button_menu({\u201CQuit\u201D}); while ( ! check_buttons(q) ) { n = check_buttons(m); draw_image(n); } }  radio_button (n) { draw_circle(get_x(), get_y(), 3); }  draw_label (string) { w = calculate_width(string); print(string, WINDOW_PORT); set_x(get_x() + w); } radio_menu(labels) { i = 0; while (i &lt; labels.size) { radio_button(i); draw_label(labels[i]); set_y(get_y() + RADIO_BUTTON_H); i++; } } 2/17/01 Vancouver Institute  25  UBC software modularity group  \u000Csimplified implementation main () { draw_label(\u201CHaida Art Browser\u201D); m = radio_menu( {\u201CWhale\u201D, \u201CEagle\u201D, \u201CDogfish\u201D}); q = button_menu({\u201CQuit\u201D}); while ( ! check_buttons(q) ) { n = check_buttons(m); draw_image(n); } }  radio_button (n) { draw_circle(get_x(), get_y(), 3); }  draw_circle (x, y, r) { %%primitive_oval(x, y, 1, r); }  draw_label (string) { w = calculate_width(string); print(string, WINDOW_PORT); set_x(get_x() + w); } radio_menu(labels) { i = 0; while (i &lt; labels.size) { radio_button(i); draw_label(labels[i]); set_y(get_y() + RADIO_BUTTON_H); i++; } } 2/17/01 Vancouver Institute  26  UBC software modularity group  \u000Csimplified implementation main () { draw_label(\u201CHaida Art Browser\u201D); m = radio_menu( {\u201CWhale\u201D, \u201CEagle\u201D, \u201CDogfish\u201D}); q = button_menu({\u201CQuit\u201D}); while ( ! check_buttons(q) ) { n = check_buttons(m); draw_image(n); } }  radio_button (n) { draw_circle(get_x(), get_y(), 3); }  draw_circle (x, y, r) { %%primitive_oval(x, y, 1, r); }  draw_label (string) { w = calculate_width(string); print(string, WINDOW_PORT); set_x(get_x() + w); } radio_menu(labels) { i = 0; while (i &lt; labels.size) { radio_button(i); draw_label(labels[i]); set_y(get_y() + RADIO_BUTTON_H); i++; } } 2/17/01 Vancouver Institute  27  UBC software modularity group  \u000Csimplified implementation main () { draw_label(\u201CHaida Art Browser\u201D); m = radio_menu( {\u201CWhale\u201D, \u201CEagle\u201D, \u201CDogfish\u201D}); q = button_menu({\u201CQuit\u201D}); while ( ! check_buttons(q) ) { n = check_buttons(m); draw_image(n); } }  draw_circle (x, y, r) { %%primitive_oval(x, y, 1, r); } button_menu(labels) { i = 0; while (i &lt; labels.size) { draw_label(labels[i]); set_y(get_y() + BUTTON_H); i++; } }  draw_label (string) { w = calculate_width(string); print(string, WINDOW_PORT); set_x(get_x() + w); } radio_menu(labels) { i = 0; while (i &lt; labels.size) { radio_button(i); draw_label(labels[i]); set_y(get_y() + RADIO_BUTTON_H); i++; } } 2/17/01 Vancouver Institute  radio_button (n) { draw_circle(get_x(), get_y(), 3); }  28  UBC software modularity group  \u000Csimplified implementation main () { draw_label(\u201CHaida Art Browser\u201D); m = radio_menu( {\u201CWhale\u201D, \u201CEagle\u201D, \u201CDogfish\u201D}); q = button_menu({\u201CQuit\u201D}); while ( ! check_buttons(q) ) { n = check_buttons(m); draw_image(n); } }  draw_circle (x, y, r) { %%primitive_oval(x, y, 1, r); } button_menu(labels) { i = 0; while (i &lt; labels.size) { draw_label(labels[i]); set_y(get_y() + BUTTON_H); i++; } }  draw_label (string) { w = calculate_width(string); print(string, WINDOW_PORT); set_x(get_x() + w); } radio_menu(labels) { i = 0; while (i &lt; labels.size) { radio_button(i); draw_label(labels[i]); set_y(get_y() + RADIO_BUTTON_H); i++; } } 2/17/01 Vancouver Institute  radio_button (n) { draw_circle(get_x(), get_y(), 3); }  29  UBC software modularity group  \u000Csimplified implementation main () { draw_label(\u201CHaida Art Browser\u201D); m = radio_menu( {\u201CWhale\u201D, \u201CEagle\u201D, \u201CDogfish\u201D}); q = button_menu({\u201CQuit\u201D}); while ( ! check_buttons(q) ) { n = check_buttons(m); draw_image(n); } }  draw_circle (x, y, r) { %%primitive_oval(x, y, 1, r); } button_menu(labels) { i = 0; while (i &lt; labels.size) { draw_label(labels[i]); set_y(get_y() + BUTTON_H); i++; } }  draw_label (string) { w = calculate_width(string); print(string, WINDOW_PORT); set_x(get_x() + w); } radio_menu(labels) { i = 0; while (i &lt; labels.size) { radio_button(i); draw_label(labels[i]); set_y(get_y() + RADIO_BUTTON_H); i++; } } 2/17/01 Vancouver Institute  radio_button (n) { draw_circle(get_x(), get_y(), 3); }  30  UBC software modularity group  \u000Csimplified implementation  ha!  main () { draw_label(\u201CHaida Art Browser\u201D); m = radio_menu( {\u201CWhale\u201D, \u201CEagle\u201D, \u201CDogfish\u201D}); q = button_menu({\u201CQuit\u201D}); while ( ! check_buttons(q) ) { n = check_buttons(m); draw_image(n); } }  draw_circle (x, y, r) { %%primitive_oval(x, y, 1, r); } button_menu(labels) { i = 0; while (i &lt; labels.size) { draw_label(labels[i]); set_y(get_y() + BUTTON_H); i++; } }  draw_label (string) { w = calculate_width(string); print(string, WINDOW_PORT); set_x(get_x() + w); } radio_menu(labels) { i = 0; while (i &lt; labels.size) { radio_button(i); draw_label(labels[i]); set_y(get_y() + RADIO_BUTTON_H); i++; } } 2/17/01 Vancouver Institute  radio_button (n) { draw_circle(get_x(), get_y(), 3); }  draw_image (img) { w = img.width; h = img.height; do (r = 0; r &lt; h; r++) do (c = 0; c &lt; w; c++) WINDOW[r][c] = img[r][c]; } 31  UBC software modularity group  \u000Csimplified implementation  ha!  main () { draw_label(\u201CHaida Art Browser\u201D); m = radio_menu( {\u201CWhale\u201D, \u201CEagle\u201D, \u201CDogfish\u201D}); q = button_menu({\u201CQuit\u201D}); while ( ! check_buttons(q) ) { n = check_buttons(m); draw_image(n); } }  draw_circle (x, y, r) { %%primitive_oval(x, y, 1, r); } button_menu(labels) { i = 0; while (i &lt; labels.size) { draw_label(labels[i]); set_y(get_y() + BUTTON_H); i++; } }  draw_label (string) { w = calculate_width(string); print(string, WINDOW_PORT); set_x(get_x() + w); } radio_menu(labels) { i = 0; while (i &lt; labels.size) { radio_button(i); draw_label(labels[i]); set_y(get_y() + RADIO_BUTTON_H); i++; } } 2/17/01 Vancouver Institute  radio_button (n) { draw_circle(get_x(), get_y(), 3); }  draw_image (img) { w = img.width; h = img.height; do (r = 0; r &lt; h; r++) do (c = 0; c &lt; w; c++) WINDOW[r][c] = img[r][c]; } 32  UBC software modularity group  \u000Cseparation of concerns main () { draw_label(\u201CHaida Art Browser\u201D); m = radio_menu( {\u201CWhale\u201D, \u201CEagle\u201D, \u201CDogfish\u201D}); q = button_menu({\u201CQuit\u201D}); while ( ! check_buttons(q) ) { n = check_buttons(m); draw_image(n); } }  draw_circle (x, y, r) { %%primitive_oval(x, y, 1, r); } button_menu(labels) { i = 0; while (i &lt; labels.size) { draw_label(labels[i]); set_y(get_y() + BUTTON_H); i++; } }  draw_label (string) { w = calculate_width(string); print(string, WINDOW_PORT); set_x(get_x() + w); } radio_menu(labels) { i = 0; while (i &lt; labels.size) { radio_button(i); draw_label(labels[i]); set_y(get_y() + RADIO_BUTTON_H); i++; } } 2/17/01 Vancouver Institute  radio_button (n) { draw_circle(get_x(), get_y(), 3); }  draw_image (img) { w = img.width; h = img.height; do (r = 0; r &lt; h; r++) do (c = 0; c &lt; w; c++) WINDOW[r][c] = img[r][c]; } 33  UBC software modularity group  \u000Cseparation of concerns main  () {  radio_menu(labels)  draw_label(\u201CHaida Art Browser\u201D); m = radio_menu( {\u201CWhale\u201D, \u201CEagle\u201D, \u201CDogfish\u201D}); q = button_menu({\u201CQuit\u201D}); while ( ! check_buttons(q) ) { n = check_buttons(m); draw_image(n); }  i = 0; while (i &lt; labels.size) { radio_button(i); draw_label(labels[i]); set_y(get_y() + RADIO_BUTTON_H); i++; }  }  }  draw_image  radio_button (n) { draw_circle(get_x(), get_y(), 3); }  (img) {  w = img.width; h = img.height; do (r = 0; r &lt; h; r++) do (c = 0; c &lt; w; c++) WINDOW[r][c] = img[r][c];  button_menu(labels)  {  i = 0; while (i &lt; labels.size) { draw_label(labels[i]); set_y(get_y() + BUTTON_H); i++; }  }  draw_label  {  (string) {  w = calculate_width(string); print(string, WINDOW_PORT); set_x(get_x() + w);  }  }  draw_circle  (x, y, r) {  %%primitive_oval(x, y, 1, r);  } 2/17/01 Vancouver Institute  34  UBC software modularity group  \u000Cprinciples for separation haida_browser: main () { draw_label(\u201CHaida Art Browser\u201D); m = radio_menu( {\u201CWhale\u201D, \u201CEagle\u201D, \u201CDogfish\u201D}); q = button_menu({\u201CQuit\u201D}); while ( ! check_buttons(q) ) { n = check_buttons(m); draw_image(n); } }  menus: radio_menu(labels) button_menu(labels) check_buttons(menu)  graphics: draw_image(img) draw_label(string) draw_circle(x, y, r)  \u2022 group by: \u2013 \u201Cshared secrets\u201D \u2013 common functionality \u2013 no upcalls  \u2022 modules with \u2013 crisp, narrow interfaces 2/17/01 Vancouver Institute  35  UBC software modularity group  \u000CPL support  module abstraction mechanisms  \u2022 clear module interfaces  module menus { exports: radio_menu(labels) button_menu(labels) check_buttons(menu) }  \u2013 explicit \u2013 enforced \u2022 only through front door \u2022 can\u2019t \u2018read the mail\u2019  \u2013 type systems \u2013 opacity  \u2022 \u2018abstraction\u2019 mechanisms \u2013 from outside can only see abstraction of module  2/17/01 Vancouver Institute  36  UBC software modularity group  \u000Cthinking architecturally  haida_browser menus  graphics  \u2022 abstraction lets us \u2013 look at overall system structure  2/17/01 Vancouver Institute  37  UBC software modularity group  \u000Cthinking architecturally  menus: radio_menu(labels) button_menu(labels) check_buttons(menu)  haida_browser  graphics  \u2022 abstraction lets us \u2013 look at overall system structure \u2013 zoom in on one part of the system at a time  2/17/01 Vancouver Institute  38  UBC software modularity group  \u000Cthinking architecturally haida_browser: main () { draw_label(\u201CHaida Browser\u201D); m = radio_menu( {\u201CWhale\u201D, \u201CEagle\u201D, \u201CDogfish\u201D}); q = button_menu({\u201CQuit\u201D}); while ( ! check_buttons(q) ) { n = check_buttons(m); draw_image(n); } }  menus  graphics  \u2022 abstraction lets us \u2013 look at overall system structure \u2013 zoom in on one part of the system at a time \u2022 more or less detail  2/17/01 Vancouver Institute  39  UBC software modularity group  \u000C\u201Cmodular programming\u201D \u2022 separation of concerns \u2013 organize code according to common functionality \u2013 PL mechanisms \u2022 enforce secrecy of module internals haida_browser menus  graphics  \u2022 abstraction \u2013 enables architectural thinking \u2013 treat the module as its interface \u2013 100 modules can feel like 1000 lines  2/17/01 Vancouver Institute  40  UBC software modularity group  \u000CPart III \u2013 systems of applications \u2022 Powerpoint, Outlook, browsers\u2026 \u2022 tangling problems arise again  2/17/01 Vancouver Institute  41  UBC software modularity group  \u000Cvariations of functionality pull-down menus toolbars combo: text box and list  toolbar buttons color choosers  even with modular programming this appears to be incredibly complex\u2026 2/17/01 Vancouver Institute  42  UBC software modularity group  \u000Ccoping with complexity \u2022 Simula [Dahl &amp; Nygaard 64, 68] \u2022 Smalltalk [Alan Kay 70 \u2013 80] \u2022 we cope with complexity all the time \u2013 world has a diversity of complex objects \u2013 abstraction, classification and specialization  \u2022 \u201Cmodel\u201D programs after the world  2/17/01 Vancouver Institute  43  UBC software modularity group  \u000C\u201Cobject-oriented programming\u201D \u2022 aka OOP \u2022 \u201Cobjects\u201D are\u2026 \u2013 animate \u2022 know how to do things \u2022 code plus data \u2022 little computers waiting to be told what to do  \u2013 classified \u2022 specializations of other objects  \u2022 a \u201Cclass\u201D is a cookie cutter for objects \u2013 specializations of other classes 2/17/01 Vancouver Institute  44  UBC software modularity group  \u000Ca class hierarchy Menu  ButtonMenu  ToggleButtonMenu  CheckBoxMenu  2/17/01 Vancouver Institute  RadioButtonMenu  45  UBC software modularity group  \u000Coperations on objects Menu  ButtonMenu  ToggleButtonMenu  display: boxes, labels click: highlight  CheckBoxMenu  RadioButtonMenu  display: boxes, maybe checks, labels click: set/clear  2/17/01 Vancouver Institute  46  display: circle, maybe dots, labels click: set/clear AND clear others  UBC software modularity group  \u000Cinheritance  classes are \u201Ccookie cutters\u201D for objects  Menu display: &lt;promise&gt; click: &lt;promise&gt;  ButtonMenu  ToggleButtonMenu  display: boxes, labels click: highlight  click:  CheckBoxMenu  RadioButtonMenu  display: boxes, maybe checks, labels click: set/clear  2/17/01 Vancouver Institute  set/clear  47  display: circle, maybe dots, labels click: set/clear AND clear others  UBC software modularity group  \u000CPL support class RadioButtonMenu extends ToggleButtonMenu { void display() { i = 0; while (i &lt; buttons.length) { drawCircle(); drawLabel(buttons[i]); if ( buttons[i].isSet() ) drawHighlight(i); } }  a \u201Csubclass\u201D of ToggleButton  defines two operations  this operation builds on the superclass\u2019s version of it  void click(i) { super(i); clearOthers(i); } } 2/17/01 Vancouver Institute  48  UBC software modularity group  \u000COOP is useful  2/17/01 Vancouver Institute  49  UBC software modularity group  \u000COOP is elegant  2/17/01 Vancouver Institute  50  UBC software modularity group  \u000COOP is powerful\u2026  2/17/01 Vancouver Institute  51  UBC software modularity group  \u000C\u201Cobject-oriented programming\u201D \u2022 objects are \u2013 code plus data \u2013 little computers \u2013 arranged in class hierarchies  \u2022 abstraction, classification &amp; specialization \u2013 think in terms of class hierarchy \u2013 OOP \u0002 OOD \u2013 write code by drawing pictures \u2022 draw class diagrams \u2022 produce class code  \u2013 only write things once!  2/17/01 Vancouver Institute  52  UBC software modularity group  \u000Ctangling \u0002 structure i = 1 TEST: if i &lt; 5 then goto BODY else goto END BODY: print(i) i = i + 1 goto TEST END:  main () { draw_label(\u201CHaida Browser\u201D); m = radio_menu( {\u201CWhale\u201D, \u201CEagle\u201D, \u201CDogfish\u201D}); q = button_menu({\u201CQuit\u201D}); while ( ! check_buttons(q) ) { n = check_buttons(m); draw_label (string) { draw_image(n); w = calculate_width(string); } print(string, WINDOW_PORT); } set_x(get_x() + w); radio_menu(labels) { } i = 0; while (i &lt; labels.size) { radio_button(i); draw_label(labels[i]); set_y(get_y() + RADIO_BUTTON_H); i++; } }  structured control constructs  i = 1 while (i &lt; 5) { print(i) i = i + 1 }  radio_button (n) { draw_circle(get_x(), get_y(), 3); } draw_circle (x, y, r) { %%primitive_oval(x, y, 1, r); } button_menu(labels) { i = 0; while (i &lt; labels.size) { draw_label(labels[i]); set_y(get_y() + BUTTON_H); i++; draw_image (img) { } } w = img.width; h = img.height; do (r = 0; r &lt; h; r++) do (c = 0; c &lt; w; c++) WINDOW[r][c] = img[r][c]; }  simple_browser menus  graphics  AbstractButton  Button  ToggleButton  CheckBox  ? 2/17/01 Vancouver Institute  53  RadioButton  modules with narrow interfaces  classification &amp; specialization of objects  crosscutting aspects UBC software modularity group  \u000CPart IV \u2013 an analogy  designing and building a simple bridge... 2/17/01 Vancouver Institute  54  UBC software modularity group  \u000Ccrosscutting models  m  simple statics  2/17/01 Vancouver Institute  more detailed statics  55  simple dynamics  UBC software modularity group  \u000Cmodels vs. artifacts abstract model  real artifact  i = 1 while (i &lt; 4) { print(i) i = i + 1 }  programs are both this is magic 2/17/01 Vancouver Institute  56  UBC software modularity group  \u000Ccrosscutting programs?  m  module menus { exports: radio_menu(labels) button_menu(labels) check_buttons(menu) }  radio_menu(labels) { i = 0; while (i &lt; labels.size) { radio_button(i); draw_label(labels[i]); set_y(get_y() + RADIO_BUTTON_H); i++; } } radio_button (n) { draw_circle(get_x(), get_y(), 3); } button_menu(labels) { i = 0; while (i &lt; labels.size) { draw_label(labels[i]); set_y(get_y() + BUTTON_H); i++; } }  2/17/01 Vancouver Institute  57  ? UBC software modularity group  \u000C\u201Caspect-oriented programming\u201D \u2022 more than one modularity is possible  vm_fault  \u2013 order of execution \u2013 context of use \u2013 inter-object collaboration  vm_pager_getpages  \u2026 vnode_pager_getpages  VM module  if (((fs.object-&gt;type != OBJT_DEFAULT) &amp;&amp; (((fault_flags &amp; VM_FAULT_WIRE_MASK) == 0) || wired)) || (fs.object == fs. first_object)) { if (f s. pindex &gt;= fs. object-&gt;size) { unlock_and_deallocate(&amp;f s) ; return (KERN_PROTECTION_FAILURE); }  \u2026  /* * Allocate a new page for this object/offset pair. */ fs.m = vm_page_alloc( fs.object, fs. p index, (fs. vp || fs.object-&gt;backing_object)? VM_ALLOC_NORMAL: VM_ALLOC_ZERO);  aspect normal_prefetching { pointcut vm_fault_cflow( vm_map_t map ): cflow( calls( int vm_fault( map, .. )));  if (f s. m == NULL) { unlock_and_deallocate(&amp;f s) ; VM_WAIT; goto RetryFault; }  pointcut ffs_getpages_cflow( vm_object_t obj, vm_page_t* plist, int len, int fpage ): cflow( calls( int ffs_getpages( obj, plist, len, fpage ))); before( vm_map_t map, vm_object_t obj, vm_page_t* plist, int len, int fpage ): calls( int vnode_pager_getpages( obj, plist, len, fpage )) &amp;&amp; vm_fault_cflow( map )  }  { (((fault_flags &amp; VM_FAULT_WIRE_MASK) == 0) || wired)) { int rv; int reqpage; int ahead, behind;  if ( obj-&gt;declared_behaviour == NORMAL ) { vm_map_lock( map ); plan_and_alloc_normal( obj, plist, len, fpage ); vm_map_unlock( map ); }  if (f s. first_object-&gt;behavior == OBJ_RANDOM) { ahead = 0; behind = 0; } else { behind = (v addr - fs.entry-&gt;start) &gt;&gt; PAGE_SHIFT; if (behind &gt; VM_FAULT_READ_BEHIND) behind = VM_FAULT_READ_BEHIND;  ffs_getpages  } after( vm_object_t obj, vm_page_t* plist, int len, int fpage, int valid ): calls( valid ffs_valid(..) ) &amp;&amp; ffs_getpages_cflow( obj, plist, len, fpage ) { if ( valid ) dealloc_all_prefetch_pages( obj, plist, len, fpage ); }  :  after( vm_object_t obj, vm_page_t* plist, int len, int fpage, int error, int reqblkno ): calls( error ufs_bmap( struct vnode*, reqblkno, ..) ) &amp;&amp; ffs_getpages_cflow( obj, plist, len, fpage ) { if ( error || (reqblkno == -1) ) dealloc_all_prefetch_pages( obj, plist, len, fpage );  else firstpindex = fs.first_pindex 2*(VM_FAULT_READ_BEHIND + VM_FAULT_READ_AHEAD + 1);  ffs_valid ufs_bmap  for(tmppindex = fs.first_pindex - 1; tmppindex &gt;= firstpindex; --t mppindex) { vm_page_t mt; mt = vm_page_lookup( fs.first_object, tmppindex) ; if (mt == NULL || (mt-&gt;valid != VM_PAGE_BITS_ALL)) break; if (mt- &gt;busy || (m t-&gt;flags &amp; (PG_BUSY | PG_FICTITIOUS)) || mt- &gt;hold_count || mt- &gt;wire_count) continue; if (mt- &gt;dirty == 0) vm_page_test_dirty(mt) ; if (mt- &gt;dirty) { vm_page_protect(mt, VM_PROT_NONE); vm_page_deactivate(m t) ; } else { vm_page_cache(m t); } }  ffs_calc_size  aspect sequential_prefetching { pointcut vm_fault_cflow( vm_map_t map ): cflow( calls( int vm_fault( map, .. ))); pointcut ffs_read_cflow( struct vnode* vp, struct uio* io_inf, int size, struct buff** bpp ): cflow( calls( int ffs_read( vp, io_inf, size, bpp ))); before( vm_map_t map, vm_object_t obj, vm_page_t* plist, int len, int fpage ): calls( int vnode_pager_getpages( obj, plist, len, fpage )) &amp;&amp; vm_fault_cflow( map ) { if ( obj-&gt;declared_behaviour == SEQUENTIAL ) { vm_map_lock( map ); plan_and_alloc_sequential( obj, plist, len, fpage ); vm_map_unlock( map ); }  ahead += behind; behind = 0; } } if (f s. first_object-&gt;behavior == OBJ_RANDOM) { ahead = 0; behind = 0; } else { behind = (v addr - fs.entry-&gt;start) &gt;&gt; PAGE_SHIFT; if (behind &gt; VM_FAULT_READ_BEHIND) behind = VM_FAULT_READ_BEHIND;  FFS module 2/17/01 Vancouver Institute  ahead = ((fs.entry-&gt;end - vaddr) &gt;&gt; PAGE_SHIFT) - 1; if (ahead &gt; VM_FAULT_READ_AHEAD) ahead = VM_FAULT_READ_AHEAD;  : 58  around( vm_object_t obj, vm_page_t* plist, int len, int fpage ): calls( int ffs_getpages( obj, plist, len, fpage )) { if ( obj-&gt;behaviour == SEQUENTIAL ) { struct vnode* vp = obj-&gt;handle; struct uio* io_inf = io_prep( plist[fpage]-&gt;pindex, MAXBSIZE, curproc ); int error = ffs_read( vp, io_inf, MAXBSIZE, curproc-&gt;p_ucred ); return cleanup_after_read( error, obj, plist, len, fpage ); } else proceed; } after( struct uio* io_info, int size, struct buf** bpp ):  UBC software modularity group  \u000Ctangling \u0002 structure i = 1 TEST: if i &lt; 5 then goto BODY else goto END BODY: print(i) i = i + 1 goto TEST END:  main () { draw_label(\u201CHaida Browser\u201D); m = radio_menu( {\u201CWhale\u201D, \u201CEagle\u201D, \u201CDogfish\u201D}); q = button_menu({\u201CQuit\u201D}); while ( ! check_buttons(q) ) { n = check_buttons(m); draw_label (string) { draw_image(n); w = calculate_width(string); } print(string, WINDOW_PORT); } set_x(get_x() + w); radio_menu(labels) { } i = 0; while (i &lt; labels.size) { radio_button(i); draw_label(labels[i]); set_y(get_y() + RADIO_BUTTON_H); i++; } }  structured control constructs  i = 1 while (i &lt; 5) { print(i) i = i + 1 }  radio_button (n) { draw_circle(get_x(), get_y(), 3); } draw_circle (x, y, r) { %%primitive_oval(x, y, 1, r); } button_menu(labels) { i = 0; while (i &lt; labels.size) { draw_label(labels[i]); set_y(get_y() + BUTTON_H); i++; draw_image (img) { } } w = img.width; h = img.height; do (r = 0; r &lt; h; r++) do (c = 0; c &lt; w; c++) WINDOW[r][c] = img[r][c]; }  simple_browser menus  graphics  AbstractButton  Button  ToggleButton  CheckBox  RadioButton  modules with narrow interfaces  classification &amp; specialization of objects  crosscutting aspects 2/17/01 Vancouver Institute  59  UBC software modularity group  "@en
<https://open.library.ubc.ca/cIRcle/collections/12708/items/1.0102688>