1 00:00:00,760 --> 00:00:02,790 So what we're going to do today is 2 00:00:02,790 --> 00:00:07,310 continue our discussion of modular computer software, 3 00:00:07,310 --> 00:00:10,150 and specifically focus on the topic 4 00:00:10,150 --> 00:00:13,960 we started talking about last time called soft modularity. 5 00:00:18,770 --> 00:00:23,730 And once we figure out, you know, finish our story 6 00:00:23,730 --> 00:00:27,720 with regard to soft modularity and understand 7 00:00:27,720 --> 00:00:30,390 exactly what this means, we're going 8 00:00:30,390 --> 00:00:33,890 to start talking about a different kind of modularity 9 00:00:33,890 --> 00:00:35,780 called enforced modularity. 10 00:00:39,187 --> 00:00:41,020 And enforced modularity is going to actually 11 00:00:41,020 --> 00:00:45,950 take us through three lectures, today and the next two lectures 12 00:00:45,950 --> 00:00:47,510 next week. 13 00:00:47,510 --> 00:00:49,830 And the topic for today in terms of enforced 14 00:00:49,830 --> 00:00:53,110 modularity is a particular way of obtaining modularity 15 00:00:53,110 --> 00:00:56,185 in computer systems called client/service organization. 16 00:01:01,530 --> 00:01:03,780 Some people call it client/server computing. 17 00:01:03,780 --> 00:01:08,100 And that's the plan for today. 18 00:01:08,100 --> 00:01:12,590 So what we saw the last time was basically a lecture describing, 19 00:01:12,590 --> 00:01:14,850 for the most part, how linking worked. 20 00:01:14,850 --> 00:01:17,560 And the idea in linking is that when 21 00:01:17,560 --> 00:01:21,370 you have a number of software modules, 22 00:01:21,370 --> 00:01:23,990 and your goal is to take all of them 23 00:01:23,990 --> 00:01:25,720 and get an executable program out 24 00:01:25,720 --> 00:01:30,450 of them that another program could load into memory and run. 25 00:01:30,450 --> 00:01:34,920 And that task was being done by a piece 26 00:01:34,920 --> 00:01:36,890 of system software called a linker, 27 00:01:36,890 --> 00:01:40,360 and out pops an executable program. 28 00:01:40,360 --> 00:01:44,790 So at the end of the lecture last time, a couple of students 29 00:01:44,790 --> 00:01:46,820 asked me two things. 30 00:01:46,820 --> 00:01:48,930 One was why we were actually talking about this. 31 00:01:48,930 --> 00:01:51,160 And the second more important question 32 00:01:51,160 --> 00:01:53,620 was why it wasn't in the notes. 33 00:01:53,620 --> 00:01:56,160 And so let me answer the first question [SOUND OFF/THEN ON] 34 00:01:56,160 --> 00:01:58,320 question first. 35 00:01:58,320 --> 00:02:01,510 The plan in lectures is to understand concepts of computer 36 00:02:01,510 --> 00:02:02,690 systems with examples. 37 00:02:02,690 --> 00:02:04,982 And oftentimes we find examples that 38 00:02:04,982 --> 00:02:06,190 aren't actually in the notes. 39 00:02:06,190 --> 00:02:08,199 And we use them, A, because if we 40 00:02:08,199 --> 00:02:09,740 don't use different examples, there's 41 00:02:09,740 --> 00:02:12,089 sort of not as much incentive to show up. 42 00:02:12,089 --> 00:02:14,380 But often because some of the examples that work better 43 00:02:14,380 --> 00:02:17,840 in lecture don't actually work out as clearly in the notes. 44 00:02:17,840 --> 00:02:20,955 So we do tend to use different examples. 45 00:02:20,955 --> 00:02:22,830 To answer the first question, why we actually 46 00:02:22,830 --> 00:02:25,350 looked at the linker, first of all 47 00:02:25,350 --> 00:02:28,790 it's a common piece of software that pretty much every program 48 00:02:28,790 --> 00:02:32,599 that you run today goes through a process of linking. 49 00:02:32,599 --> 00:02:34,140 But what it actually allowed us to do 50 00:02:34,140 --> 00:02:38,490 was illustrate two main concepts in naming 51 00:02:38,490 --> 00:02:41,322 having to do with the way in which the main mapping 52 00:02:41,322 --> 00:02:42,030 algorithm worked. 53 00:02:46,290 --> 00:02:47,970 And in the context of the linker, 54 00:02:47,970 --> 00:02:49,880 the problem was to take these symbols 55 00:02:49,880 --> 00:02:53,970 that you find in the program, and basically resolve them, 56 00:02:53,970 --> 00:02:55,970 in other words, find out where they are defined, 57 00:02:55,970 --> 00:02:58,400 and where the instructions corresponding to those symbols, 58 00:02:58,400 --> 00:03:00,390 or where the data corresponding to the symbol 59 00:03:00,390 --> 00:03:03,140 was actually located. 60 00:03:03,140 --> 00:03:07,900 And the concepts that we saw were two different concepts. 61 00:03:07,900 --> 00:03:14,530 The first was name mapping using a table lookup, where 62 00:03:14,530 --> 00:03:16,820 within each object file there was a symbol table that 63 00:03:16,820 --> 00:03:19,590 mapped between the symbols found in a module 64 00:03:19,590 --> 00:03:23,350 to the location where the symbols were defined further. 65 00:03:23,350 --> 00:03:27,870 And another example of doing name mapping, which 66 00:03:27,870 --> 00:03:30,500 was the process of search through a series of contexts. 67 00:03:33,930 --> 00:03:36,310 And in particular, we looked at the problem 68 00:03:36,310 --> 00:03:42,080 of when you are in the context of LD, which GCC uses when 69 00:03:42,080 --> 00:03:44,590 it finds, goes through a sequence of dot O 70 00:03:44,590 --> 00:03:46,500 files as well as libraries on the command 71 00:03:46,500 --> 00:03:51,770 line, what algorithm it actually uses to resolve its symbols. 72 00:03:51,770 --> 00:03:55,930 And I realize now that what I had left out on the board, 73 00:03:55,930 --> 00:03:58,160 there was a couple of mistakes in the algorithm, 74 00:03:58,160 --> 00:04:00,000 and I asked what mistakes were. 75 00:04:00,000 --> 00:04:04,681 And I realized I didn't show you what the actual algorithm is 76 00:04:04,681 --> 00:04:05,180 correctly. 77 00:04:05,180 --> 00:04:07,037 So I thought I'd spend a minute doing that 78 00:04:07,037 --> 00:04:09,120 so that if you have something wrong in your notes, 79 00:04:09,120 --> 00:04:12,200 you can fix that up, because I actually never said 80 00:04:12,200 --> 00:04:13,690 what the right thing was. 81 00:04:13,690 --> 00:04:15,360 So if you recall, the general problem 82 00:04:15,360 --> 00:04:19,010 was you have GCC running on a set of dot O files, 83 00:04:19,010 --> 00:04:21,990 F1 dot O all the way through Fn dot O. 84 00:04:21,990 --> 00:04:26,790 And what we're trying to do is describe an algorithm where 85 00:04:26,790 --> 00:04:30,214 when you obtain the I'th object file and you have a set 86 00:04:30,214 --> 00:04:32,380 of currently defined symbols, and a set of currently 87 00:04:32,380 --> 00:04:36,060 undefined symbols, how you can maintain three sets: 88 00:04:36,060 --> 00:04:38,340 the set of object files that go into the executable, 89 00:04:38,340 --> 00:04:41,090 the set of defined symbols that have been seen so far, 90 00:04:41,090 --> 00:04:44,170 and the set of undefined symbols that have been seen so far. 91 00:04:44,170 --> 00:04:46,840 And you want to keep updating that. 92 00:04:46,840 --> 00:04:50,390 So one way to easily see what's going on is with a picture. 93 00:04:50,390 --> 00:04:54,270 So up until now, until you've finished I minus one files, 94 00:04:54,270 --> 00:04:58,710 let's say you've built up a set, U, of all 95 00:04:58,710 --> 00:05:02,990 of the undefined symbols that have been encountered so far. 96 00:05:02,990 --> 00:05:05,532 And likewise, you have another set, D, of all the symbols 97 00:05:05,532 --> 00:05:07,740 that have been defined so far that you've encountered 98 00:05:07,740 --> 00:05:09,280 and have been defined so far. 99 00:05:09,280 --> 00:05:11,580 So, D and U dynamically change as you 100 00:05:11,580 --> 00:05:14,242 go from left to right through the sequence of files. 101 00:05:14,242 --> 00:05:15,700 Now, when you are on the I'th file, 102 00:05:15,700 --> 00:05:18,140 there is a set of symbols that have been defined that are 103 00:05:18,140 --> 00:05:20,600 going to be defined in the I'th file. 104 00:05:20,600 --> 00:05:23,910 And that set does not intersect with a set, D, 105 00:05:23,910 --> 00:05:27,730 because if it did, then you have an overlapping defined symbol 106 00:05:27,730 --> 00:05:28,900 and that's an error. 107 00:05:28,900 --> 00:05:32,340 So the interesting case is to look at this kind of an example 108 00:05:32,340 --> 00:05:35,960 where you have a set, Di, of the symbols that were defined 109 00:05:35,960 --> 00:05:38,630 in the I'th file. 110 00:05:38,630 --> 00:05:41,770 And likewise, in the I'th file, there are going to be a set 111 00:05:41,770 --> 00:05:44,100 of undefined symbols. 112 00:05:44,100 --> 00:05:46,990 And clearly, that set doesn't overlap with a set, Di, 113 00:05:46,990 --> 00:05:48,470 because if it's undefined, it can't 114 00:05:48,470 --> 00:05:50,420 be defined in the same file. 115 00:05:50,420 --> 00:05:54,670 So that said, in general, looks something like this. 116 00:05:54,670 --> 00:05:58,190 It has some symbols undefined in this object file that 117 00:05:58,190 --> 00:06:00,500 are also undefined previously. 118 00:06:00,500 --> 00:06:02,690 Some symbols that are undefined in this file that 119 00:06:02,690 --> 00:06:05,240 have been defined previously, and some symbols that 120 00:06:05,240 --> 00:06:07,240 have been undefined here that you've have really 121 00:06:07,240 --> 00:06:08,080 never seen before. 122 00:06:10,830 --> 00:06:12,480 So you've got to update to things. 123 00:06:12,480 --> 00:06:13,940 So D gets updated pretty easily. 124 00:06:13,940 --> 00:06:16,570 D just becomes D union Di. 125 00:06:16,570 --> 00:06:18,990 And if D intersection Di is not null, 126 00:06:18,990 --> 00:06:21,390 then you know there's an error. 127 00:06:21,390 --> 00:06:24,080 And now you need to update U, and there are many ways 128 00:06:24,080 --> 00:06:25,830 to do it that are more efficient than what 129 00:06:25,830 --> 00:06:26,871 we're going to write out. 130 00:06:26,871 --> 00:06:28,990 But it's pretty easy to see that U 131 00:06:28,990 --> 00:06:36,100 needs to get updated by unioning the current set with Ui. 132 00:06:36,100 --> 00:06:38,587 So that kind of gives you this together with that. 133 00:06:38,587 --> 00:06:40,420 But now, you have to subtract out everything 134 00:06:40,420 --> 00:06:41,890 that's been defined already. 135 00:06:41,890 --> 00:06:45,020 And since we updated D first, we could do that very easily 136 00:06:45,020 --> 00:06:48,596 by just subtracting out the set of all defined symbols. 137 00:06:48,596 --> 00:06:50,220 And you run this through until the end. 138 00:06:50,220 --> 00:06:52,820 And if you find that in the end U is not null, 139 00:06:52,820 --> 00:06:55,390 then you know that there's an undefined symbol 140 00:06:55,390 --> 00:06:57,140 so that the linking doesn't actually work. 141 00:06:57,140 --> 00:07:00,090 You can produce an executable out of it with static linking, 142 00:07:00,090 --> 00:07:00,590 OK? 143 00:07:03,130 --> 00:07:08,090 OK, so when you do combined programs in this fashion 144 00:07:08,090 --> 00:07:11,940 to produce an executable, there are all these different modules 145 00:07:11,940 --> 00:07:16,390 that have been brought together to run in an interpreter. 146 00:07:16,390 --> 00:07:18,350 And you have to ask, what kind of properties 147 00:07:18,350 --> 00:07:20,410 that program ends up having. 148 00:07:20,410 --> 00:07:23,340 What kind of modularity do you get by combining these modules 149 00:07:23,340 --> 00:07:24,570 together in this fashion? 150 00:07:24,570 --> 00:07:27,940 It will turn out that modularity is, 151 00:07:27,940 --> 00:07:31,230 it's a form of modularity called soft modularity. 152 00:07:31,230 --> 00:07:33,550 And to understand why, you have to understand 153 00:07:33,550 --> 00:07:37,860 what the interfaces between the different modules look like. 154 00:07:37,860 --> 00:07:39,550 Basically when you look at a C program, 155 00:07:39,550 --> 00:07:41,966 and you saw an example last time of how these modules hook 156 00:07:41,966 --> 00:07:45,580 together, the different modules track with one another 157 00:07:45,580 --> 00:07:47,140 through procedures. 158 00:07:47,140 --> 00:07:49,454 And procedures between modules have 159 00:07:49,454 --> 00:07:51,370 something that I'll call a procedure contract. 160 00:07:57,047 --> 00:07:59,380 And really, to understand the property of the modularity 161 00:07:59,380 --> 00:08:01,664 that you get from procedural contract, 162 00:08:01,664 --> 00:08:03,080 we need to understand a little bit 163 00:08:03,080 --> 00:08:04,940 about what happens underneath the callers 164 00:08:04,940 --> 00:08:08,120 when a caller of a procedure invokes 165 00:08:08,120 --> 00:08:09,410 a callee of a procedure. 166 00:08:09,410 --> 00:08:12,240 And this is actually material from 004. 167 00:08:12,240 --> 00:08:16,170 So if you have forgotten, I'll refresh your memory 168 00:08:16,170 --> 00:08:20,070 a little bit about it. 169 00:08:20,070 --> 00:08:22,440 So, very abstractly, if you look at a computer, 170 00:08:22,440 --> 00:08:27,500 it's got a processor in it that actually executes instructions, 171 00:08:27,500 --> 00:08:29,261 and it has a chunk of memory. 172 00:08:29,261 --> 00:08:31,260 And in that memory, there is a portion of memory 173 00:08:31,260 --> 00:08:34,289 that corresponds to the stack which is really 174 00:08:34,289 --> 00:08:37,210 where procedures, the interesting stuff 175 00:08:37,210 --> 00:08:40,000 with procedures gets implemented. 176 00:08:40,000 --> 00:08:41,909 And you also have a bunch of registers, 177 00:08:41,909 --> 00:08:44,930 so, inside the processor. 178 00:08:44,930 --> 00:08:48,650 And you have a special variable here 179 00:08:48,650 --> 00:08:50,950 called the stack pointer, which keeps 180 00:08:50,950 --> 00:08:53,590 track of where the current head of the stack 181 00:08:53,590 --> 00:08:56,060 is that you can then start pulling elements off. 182 00:08:58,840 --> 00:09:01,200 The general plan, the caller and the callee 183 00:09:01,200 --> 00:09:04,510 interact with one another by means of the stack. 184 00:09:04,510 --> 00:09:09,430 So when a caller wants to invoke the callee, what it does 185 00:09:09,430 --> 00:09:11,350 is it takes arguments of the procedure, 186 00:09:11,350 --> 00:09:14,600 and pushes them on to the stack one after another. 187 00:09:14,600 --> 00:09:17,550 Then the last thing it does is to tell the callee 188 00:09:17,550 --> 00:09:21,400 where it should return control after the procedure function 189 00:09:21,400 --> 00:09:22,590 has actually been executed. 190 00:09:22,590 --> 00:09:25,850 And that's the last thing that pushed on top of the stack 191 00:09:25,850 --> 00:09:28,620 is the [NOISE OBSCURES]. 192 00:09:28,620 --> 00:09:32,500 So then, after it does that, the caller then jumps to a location 193 00:09:32,500 --> 00:09:35,040 where the callee's module is located, 194 00:09:35,040 --> 00:09:38,380 and then control passes to the callee. 195 00:09:38,380 --> 00:09:41,194 What the callee then does is it finds out 196 00:09:41,194 --> 00:09:43,110 what the return address is, pops the arguments 197 00:09:43,110 --> 00:09:45,670 one after the other, and then goes ahead and runs 198 00:09:45,670 --> 00:09:46,880 the function. 199 00:09:46,880 --> 00:09:49,390 And then at the end of that, it looks at the return address 200 00:09:49,390 --> 00:09:50,860 and passes control back. 201 00:09:50,860 --> 00:09:55,390 And before it does that, it actually puts the answer. 202 00:09:55,390 --> 00:09:58,930 Let's assume that it puts the answer in a special register. 203 00:09:58,930 --> 00:10:00,940 And that's part of the contract as well. 204 00:10:04,880 --> 00:10:08,580 And once the caller gets the control back from the callee, 205 00:10:08,580 --> 00:10:11,450 it can proceed as before. 206 00:10:11,450 --> 00:10:13,660 Now, the important thing about this way 207 00:10:13,660 --> 00:10:17,510 of interacting between caller and callee with procedure stack 208 00:10:17,510 --> 00:10:22,536 is this contract has to obey an invariant or discipline called 209 00:10:22,536 --> 00:10:23,410 the stack discipline. 210 00:10:31,196 --> 00:10:32,820 And the essence of the stack discipline 211 00:10:32,820 --> 00:10:35,800 is that the callee should leave the stack exactly 212 00:10:35,800 --> 00:10:41,320 the way the caller left it when it invoked the callee, which 213 00:10:41,320 --> 00:10:43,650 means the caller had set up a bunch of arguments on it, 214 00:10:43,650 --> 00:10:47,340 and it but the return address on it. 215 00:10:47,340 --> 00:10:49,050 The callee should leave things as is. 216 00:10:49,050 --> 00:10:50,900 And in fact, the callee is not allowed to touch anything. 217 00:10:50,900 --> 00:10:52,733 It should leave everything as is this pretty 218 00:10:52,733 --> 00:10:55,756 much except for the register that has the answer. 219 00:10:55,756 --> 00:10:57,630 And as long as this discipline is maintained, 220 00:10:57,630 --> 00:11:00,255 and that invariant is maintained across procedure implications, 221 00:11:00,255 --> 00:11:02,630 this model of using stacks is extremely powerful. 222 00:11:02,630 --> 00:11:05,544 You could implement all sorts of procedures, nested procedure, 223 00:11:05,544 --> 00:11:07,960 I mean, recursive procedure, mutually recursive procedures 224 00:11:07,960 --> 00:11:11,970 and so on because each of these implications of the procedure 225 00:11:11,970 --> 00:11:14,750 has a certain portion of the stack that corresponds 226 00:11:14,750 --> 00:11:16,290 to an activation frame. 227 00:11:16,290 --> 00:11:18,670 And as long as this discipline is maintained, 228 00:11:18,670 --> 00:11:22,640 you can do quite complicated and interesting combinations 229 00:11:22,640 --> 00:11:25,470 of modules. 230 00:11:25,470 --> 00:11:30,610 But the problem is that that modularity depends crucially 231 00:11:30,610 --> 00:11:33,140 on the stack discipline being maintained. 232 00:11:33,140 --> 00:11:35,450 And any violation of [SOUND OFF/THEN ON] callee 233 00:11:35,450 --> 00:11:39,480 can disrupt the caller and bring it down. 234 00:11:39,480 --> 00:11:41,560 And there are many ways in which this discipline 235 00:11:41,560 --> 00:11:42,930 could be violated. 236 00:11:42,930 --> 00:11:45,160 And the easiest one is that there 237 00:11:45,160 --> 00:11:46,794 is some error or bug in the callee, 238 00:11:46,794 --> 00:11:48,210 and the callee corrupts the stack. 239 00:11:54,040 --> 00:11:55,817 Or the callee corrupts the stack pointer, 240 00:11:55,817 --> 00:11:57,650 so it actually [SOUND OFF/THEN ON] control, 241 00:11:57,650 --> 00:11:59,530 but the stack pointer points somewhere else 242 00:11:59,530 --> 00:12:06,530 and some bad instruction runs, or you have a problem. 243 00:12:06,530 --> 00:12:09,490 Now, another problem is that the callee crashes. 244 00:12:15,460 --> 00:12:17,210 For instance, there is a divide by zero, 245 00:12:17,210 --> 00:12:18,876 or there is some other violation that 246 00:12:18,876 --> 00:12:20,000 causes the callee to crash. 247 00:12:20,000 --> 00:12:23,670 And then the caller comes crashing down as well. 248 00:12:29,342 --> 00:12:31,550 And there's a bunch of other reasons, but all of them 249 00:12:31,550 --> 00:12:33,770 have to do with the stack discipline being violated, 250 00:12:33,770 --> 00:12:36,040 or with the callee crashing and control never 251 00:12:36,040 --> 00:12:39,350 returning to the caller, which means 252 00:12:39,350 --> 00:12:42,530 that the caller and the callee share fate. 253 00:12:42,530 --> 00:12:45,330 If something bad happens to the person who has called, 254 00:12:45,330 --> 00:12:50,220 sorry, the callee, then the caller struggles as well 255 00:12:50,220 --> 00:12:52,110 and isn't able to continue. 256 00:12:57,790 --> 00:13:00,510 So colloquially this is referred to as fate sharing. 257 00:13:03,940 --> 00:13:06,000 And the resulting modularity is soft 258 00:13:06,000 --> 00:13:10,070 because any fault or error in the callee affects the caller. 259 00:13:10,070 --> 00:13:13,760 The caller, there isn't any kind of a firewall 260 00:13:13,760 --> 00:13:17,067 where errors in the callee are insulated 261 00:13:17,067 --> 00:13:18,150 from errors in the caller. 262 00:13:18,150 --> 00:13:21,000 There's no shielding between the caller and callee. 263 00:13:21,000 --> 00:13:24,440 And, where is this thing going? 264 00:13:24,440 --> 00:13:27,750 Like, all right, so there's no insulation 265 00:13:27,750 --> 00:13:28,850 between caller and callee. 266 00:13:28,850 --> 00:13:32,980 And the resulting modularity is not as hard 267 00:13:32,980 --> 00:13:38,990 as we would like it to be. 268 00:13:38,990 --> 00:13:43,240 So this is the problem we'd like to solve today. 269 00:13:43,240 --> 00:13:46,090 And the first solution we're going to discuss 270 00:13:46,090 --> 00:13:53,070 is a way of organizing callers and callees 271 00:13:53,070 --> 00:13:56,430 into an organization called client service organization. 272 00:14:04,440 --> 00:14:06,650 And the main idea is going to actually involve 273 00:14:06,650 --> 00:14:10,280 a different abstraction by which callers and callees communicate 274 00:14:10,280 --> 00:14:12,650 with one another from the abstractions 275 00:14:12,650 --> 00:14:13,782 we've seen already. 276 00:14:13,782 --> 00:14:15,490 We've already seen the memory abstraction 277 00:14:15,490 --> 00:14:19,340 where you could write values to a name, 278 00:14:19,340 --> 00:14:21,775 and another person could read from it. 279 00:14:21,775 --> 00:14:23,900 And we've already seen the interpreter abstraction. 280 00:14:23,900 --> 00:14:27,760 It could turn out we are going to use a different abstraction 281 00:14:27,760 --> 00:14:31,950 A location path abstraction to implement the client service 282 00:14:31,950 --> 00:14:34,210 organization. 283 00:14:34,210 --> 00:14:37,710 And the idea is the following. 284 00:14:37,710 --> 00:14:39,640 The program is going to be decomposed 285 00:14:39,640 --> 00:14:41,750 into clients and services. 286 00:14:41,750 --> 00:14:43,860 And you might have many clients and many services, 287 00:14:43,860 --> 00:14:45,540 and you could have a client which 288 00:14:45,540 --> 00:14:47,670 is a client of one service and service in turn 289 00:14:47,670 --> 00:14:50,510 is a client of yet another service and complicated things 290 00:14:50,510 --> 00:14:52,170 like that. 291 00:14:52,170 --> 00:14:54,060 But any pair-wise interaction is going 292 00:14:54,060 --> 00:14:58,680 to be between a client and a service. 293 00:14:58,680 --> 00:15:01,610 And think of mapping that example onto here. 294 00:15:01,610 --> 00:15:04,567 Think of the callee, for example, being the service 295 00:15:04,567 --> 00:15:05,900 and the caller being the client. 296 00:15:05,900 --> 00:15:08,740 The caller wants some work done, so it's the client. 297 00:15:08,740 --> 00:15:13,150 And it invokes the service, the callee, to get that work done. 298 00:15:13,150 --> 00:15:16,020 And the plan is going to be that the client and the service 299 00:15:16,020 --> 00:15:18,240 are going to run on different computers, physically 300 00:15:18,240 --> 00:15:19,781 different computers, and we are going 301 00:15:19,781 --> 00:15:23,300 to connect the computers up with wire. 302 00:15:23,300 --> 00:15:27,160 And the idea is the moment you do that, the crash of a callee 303 00:15:27,160 --> 00:15:29,146 doesn't actually bring the caller coming down 304 00:15:29,146 --> 00:15:31,520 because it's running on a completely different processor. 305 00:15:31,520 --> 00:15:33,730 The stack is not shared. 306 00:15:33,730 --> 00:15:35,880 The memory is not shared. 307 00:15:35,880 --> 00:15:37,500 The stack point is not shared. 308 00:15:37,500 --> 00:15:41,320 There's really no problem with regard to the callee crashing, 309 00:15:41,320 --> 00:15:42,510 bringing the caller down. 310 00:15:42,510 --> 00:15:45,950 Of course, we now need a way by which the client can 311 00:15:45,950 --> 00:15:47,720 communicate its arguments to the service, 312 00:15:47,720 --> 00:15:49,803 and the service can communicate its arguments back 313 00:15:49,803 --> 00:15:50,480 to the client. 314 00:15:50,480 --> 00:15:51,960 Previously, we did the first one. 315 00:15:51,960 --> 00:15:57,660 The arguments were communicated by putting them using memory 316 00:15:57,660 --> 00:16:01,490 on the stack, and the answers were coming back to us 317 00:16:01,490 --> 00:16:03,110 from register. 318 00:16:03,110 --> 00:16:05,380 And we don't have that shared state anymore. 319 00:16:05,380 --> 00:16:09,515 So, we're going to have to implement that using messages. 320 00:16:09,515 --> 00:16:11,140 And we're going to take these messages, 321 00:16:11,140 --> 00:16:12,870 use the communication path abstraction, 322 00:16:12,870 --> 00:16:16,940 and send messages from the client to the service. 323 00:16:16,940 --> 00:16:20,660 So imagine that time flows downwards starting from when 324 00:16:20,660 --> 00:16:24,340 the client invokes the service. 325 00:16:24,340 --> 00:16:25,790 A message is sent from the client 326 00:16:25,790 --> 00:16:28,800 as a message to the service saying here's 327 00:16:28,800 --> 00:16:31,620 all the arguments, and here's the procedure 328 00:16:31,620 --> 00:16:33,180 that I want you to run. 329 00:16:33,180 --> 00:16:37,020 And it takes that information up, somehow packages it up 330 00:16:37,020 --> 00:16:39,560 into a message, and calls send. 331 00:16:39,560 --> 00:16:42,030 OK, and the assumption is that the client somehow 332 00:16:42,030 --> 00:16:45,100 already knows something about the name of the service 333 00:16:45,100 --> 00:16:47,380 or the location of the service. 334 00:16:47,380 --> 00:16:50,490 That's outside of the scope of the current discussion. 335 00:16:50,490 --> 00:16:53,020 Let's pretend somebody tells you that here's 336 00:16:53,020 --> 00:16:54,970 where the service is running that can 337 00:16:54,970 --> 00:16:57,000 run this function for you. 338 00:16:57,000 --> 00:17:00,500 So it takes the arguments in the name of the procedure, 339 00:17:00,500 --> 00:17:04,180 packages it up the message, and send it across. 340 00:17:04,180 --> 00:17:05,950 When the service gets the message. 341 00:17:05,950 --> 00:17:09,040 It validates the message to make sure that it's the right sizes, 342 00:17:09,040 --> 00:17:13,420 and it's not too big, and so on. 343 00:17:13,420 --> 00:17:17,544 And then, it takes this message and then does some processing 344 00:17:17,544 --> 00:17:18,210 on that message. 345 00:17:18,210 --> 00:17:19,760 The technical term for it is going 346 00:17:19,760 --> 00:17:22,010 to be called un-marshalling because when 347 00:17:22,010 --> 00:17:24,740 we took these arguments and put into a message, 348 00:17:24,740 --> 00:17:27,240 that process is called marshalling. 349 00:17:27,240 --> 00:17:29,500 The service is going to un-marshall this message 350 00:17:29,500 --> 00:17:32,360 and obtain the actual arguments and the name of the procedure, 351 00:17:32,360 --> 00:17:34,140 and then it's going to run it. 352 00:17:40,890 --> 00:17:44,970 I don't know if it's one L or two L's. 353 00:17:44,970 --> 00:17:48,430 And then it's going to run the procedure that's named here. 354 00:17:48,430 --> 00:17:49,920 And it's going to find the answer. 355 00:17:49,920 --> 00:17:50,980 And then when it gets the answer, 356 00:17:50,980 --> 00:17:52,330 it does the same thing back. 357 00:17:52,330 --> 00:17:55,000 It puts it back into the message and sends it across 358 00:17:55,000 --> 00:17:55,724 to the client. 359 00:17:55,724 --> 00:17:57,640 And now the client is waiting for this message 360 00:17:57,640 --> 00:18:01,060 because it sends off the message to the service 361 00:18:01,060 --> 00:18:02,270 to run this thing. 362 00:18:02,270 --> 00:18:03,812 It gets this answer back. 363 00:18:03,812 --> 00:18:04,770 It does the same thing. 364 00:18:04,770 --> 00:18:07,960 It takes the message in that it recovers the answer from it, 365 00:18:07,960 --> 00:18:09,350 and then it runs continuously. 366 00:18:13,600 --> 00:18:18,930 So this is the basic idea in client/server organization. 367 00:18:18,930 --> 00:18:21,590 And the way in which we solve this problem 368 00:18:21,590 --> 00:18:24,610 is that these two problems are solved because the callee can't 369 00:18:24,610 --> 00:18:26,950 really corrupt the stack or the stack point 370 00:18:26,950 --> 00:18:29,070 or anything else that in this model 371 00:18:29,070 --> 00:18:31,812 would have affected the caller. 372 00:18:31,812 --> 00:18:33,770 And because we have put them both on physically 373 00:18:33,770 --> 00:18:35,640 different computers and hooked them up with, 374 00:18:35,640 --> 00:18:39,630 let's say, a wire, the service crashing does not actually 375 00:18:39,630 --> 00:18:43,580 bring the client, if the service decides that it crashes, 376 00:18:43,580 --> 00:18:46,560 then the client actually doesn't come crashing down. 377 00:18:46,560 --> 00:18:48,130 Of course, the client has to somehow 378 00:18:48,130 --> 00:18:51,140 have a plan by which it knows that the service is still, 379 00:18:51,140 --> 00:18:52,810 for example, the client has to know 380 00:18:52,810 --> 00:18:55,393 whether the service has crashed or whether the service is just 381 00:18:55,393 --> 00:18:57,360 taking a long time to run something. 382 00:18:57,360 --> 00:19:00,300 That's something we have to address, and we will in a bit. 383 00:19:00,300 --> 00:19:03,740 But as long as the client is able to do that, 384 00:19:03,740 --> 00:19:06,160 a service going away or crashing is not really 385 00:19:06,160 --> 00:19:11,640 going to bring the caller or the client down with it. 386 00:19:11,640 --> 00:19:13,420 So, some properties of this organization 387 00:19:13,420 --> 00:19:14,961 are, first of all, that it's modular. 388 00:19:14,961 --> 00:19:16,720 It has essentially the same modularity 389 00:19:16,720 --> 00:19:19,690 as we had with procedures because if you 390 00:19:19,690 --> 00:19:21,190 had enough computers, you could move 391 00:19:21,190 --> 00:19:24,130 all of the different procedures on different computers, all 392 00:19:24,130 --> 00:19:25,590 of the caller/callee relationships, 393 00:19:25,590 --> 00:19:27,490 and you can preserve, essentially, 394 00:19:27,490 --> 00:19:29,880 the same modularity that you had before. 395 00:19:33,540 --> 00:19:37,960 Moreover, this modularity has a different adjective 396 00:19:37,960 --> 00:19:39,970 in front of it different from soft. 397 00:19:39,970 --> 00:19:41,340 This modularity is enforced. 398 00:19:45,770 --> 00:19:48,330 What that means is not only is it 399 00:19:48,330 --> 00:19:53,830 a modular organization, it's one where errors of, for example, 400 00:19:53,830 --> 00:19:58,420 things where one module fails or crashes 401 00:19:58,420 --> 00:20:00,420 does not bring the other one come crashing down. 402 00:20:00,420 --> 00:20:02,830 So the modularity is more enforced 403 00:20:02,830 --> 00:20:07,180 than when they were both running on the same computer using 404 00:20:07,180 --> 00:20:08,200 the procedure interface. 405 00:20:10,780 --> 00:20:12,900 And the third property of this kind of modularity 406 00:20:12,900 --> 00:20:14,210 is something already mentioned. 407 00:20:14,210 --> 00:20:19,222 It lies on the message abstraction, actually 408 00:20:19,222 --> 00:20:20,680 the communication path abstraction. 409 00:20:24,050 --> 00:20:29,990 The client and service communicate with each other 410 00:20:29,990 --> 00:20:31,192 through messages. 411 00:20:31,192 --> 00:20:32,650 And these aren't actually messages. 412 00:20:32,650 --> 00:20:36,140 You can't just sort of take a random string of bytes 413 00:20:36,140 --> 00:20:38,237 and send it to the service. 414 00:20:38,237 --> 00:20:39,820 It's actually messages that correspond 415 00:20:39,820 --> 00:20:41,150 to a particular format. 416 00:20:41,150 --> 00:20:43,070 And these are really known in advance. 417 00:20:43,070 --> 00:20:44,970 So, that way the service isn't surprised 418 00:20:44,970 --> 00:20:46,690 and the client isn't surprised when 419 00:20:46,690 --> 00:20:49,545 messages that don't conform to that pattern arrive. 420 00:20:49,545 --> 00:20:51,420 I mean, you know exactly what kind of message 421 00:20:51,420 --> 00:20:52,140 is going to arrive. 422 00:20:52,140 --> 00:20:53,514 And anything that doesn't conform 423 00:20:53,514 --> 00:20:55,655 to what is agreed upon in advance is rejected. 424 00:20:58,160 --> 00:21:00,980 But you basically make it so that you explicitly 425 00:21:00,980 --> 00:21:03,270 declare the nature of these messages much 426 00:21:03,270 --> 00:21:06,630 like you did the nature of procedural interface. 427 00:21:06,630 --> 00:21:08,630 But now, because you've physically separated it, 428 00:21:08,630 --> 00:21:11,630 you have a more enforced modularity 429 00:21:11,630 --> 00:21:13,130 than in the previous model. 430 00:21:17,574 --> 00:21:18,990 Of course, nothing comes for free. 431 00:21:18,990 --> 00:21:21,070 It's not like you got this enforced modularity, 432 00:21:21,070 --> 00:21:24,105 and you have all of these nice properties that you did before. 433 00:21:27,360 --> 00:21:29,710 Here, you had a nice property that the callee 434 00:21:29,710 --> 00:21:33,050 could, has the property that either when 435 00:21:33,050 --> 00:21:37,580 it runs and it returns to you, you know exactly what happened. 436 00:21:37,580 --> 00:21:41,469 And if it doesn't return, you know that you usually 437 00:21:41,469 --> 00:21:42,260 come crashing down. 438 00:21:42,260 --> 00:21:44,634 If the callee doesn't return, it means that control never 439 00:21:44,634 --> 00:21:46,590 comes back to the caller. 440 00:21:46,590 --> 00:21:48,515 So it's not like the caller is left 441 00:21:48,515 --> 00:21:50,890 wondering what really happened because the caller doesn't 442 00:21:50,890 --> 00:21:52,020 get control again. 443 00:21:54,549 --> 00:21:55,590 Here, you have a problem. 444 00:21:55,590 --> 00:21:59,620 If the callee, the service doesn't return back 445 00:21:59,620 --> 00:22:01,280 to the client, the client actually 446 00:22:01,280 --> 00:22:04,060 doesn't know what's going on. 447 00:22:04,060 --> 00:22:07,040 When you have two machines, two computers connected over a wire 448 00:22:07,040 --> 00:22:09,050 or over a network, it's extremely hard 449 00:22:09,050 --> 00:22:13,000 to distinguish between a service running really, really slow, 450 00:22:13,000 --> 00:22:16,550 and a service that's gone away. 451 00:22:16,550 --> 00:22:20,490 And we'll revisit this a few different times in the course. 452 00:22:20,490 --> 00:22:24,180 But it's going to be impossible for us to tell for sure, 453 00:22:24,180 --> 00:22:25,964 although we're going to try very hard. 454 00:22:25,964 --> 00:22:28,130 It's going to be really hard for us to tell for sure 455 00:22:28,130 --> 00:22:30,995 whether something exactly happened. 456 00:22:30,995 --> 00:22:32,370 And if the service didn't return, 457 00:22:32,370 --> 00:22:35,630 we don't really know for sure without much more machinery 458 00:22:35,630 --> 00:22:38,310 whether it was just that the service is still running, 459 00:22:38,310 --> 00:22:43,020 or whether it's crashed, and we are just waiting. 460 00:22:43,020 --> 00:22:47,540 And so, this organization requires a timer at the client, 461 00:22:47,540 --> 00:22:50,009 and there are many names given to this timer. 462 00:22:50,009 --> 00:22:51,550 I mean, people call them keep-alives, 463 00:22:51,550 --> 00:22:53,420 or people call them with various names. 464 00:22:53,420 --> 00:22:57,850 I'm going to call it a watchdog timer, where 465 00:22:57,850 --> 00:23:00,570 the client has to keep track using 466 00:23:00,570 --> 00:23:03,025 some kind of a timer of the service. 467 00:23:03,025 --> 00:23:05,400 And if the service doesn't return within a certain period 468 00:23:05,400 --> 00:23:08,490 of time, the client has to time out and say, 469 00:23:08,490 --> 00:23:12,479 well, the service didn't return, and I'm not 470 00:23:12,479 --> 00:23:13,520 quite sure what happened. 471 00:23:13,520 --> 00:23:16,760 It might be that the procedure I wanted to execute had ran, 472 00:23:16,760 --> 00:23:18,040 but I didn't get the answer. 473 00:23:18,040 --> 00:23:20,390 Or it might be that the procedure didn't 474 00:23:20,390 --> 00:23:23,670 get executed at all, and I have to deal with it. 475 00:23:23,670 --> 00:23:25,880 And you might be able to, by retrying the procedure, 476 00:23:25,880 --> 00:23:27,630 or you might contact another service which 477 00:23:27,630 --> 00:23:29,772 provides the same functionality, but the client 478 00:23:29,772 --> 00:23:30,980 has to deal with all of that. 479 00:23:35,930 --> 00:23:38,280 So fundamental to this client's organization 480 00:23:38,280 --> 00:23:42,340 is the notion of a time out. 481 00:23:42,340 --> 00:23:45,600 And we didn't have that here because here, 482 00:23:45,600 --> 00:23:49,630 if the callee decides that it's just going to continue on 483 00:23:49,630 --> 00:23:52,351 and not return, the caller never gets a message back. 484 00:23:52,351 --> 00:23:54,100 So, it doesn't have this decision to make. 485 00:23:54,100 --> 00:23:56,160 There is no such notion of a watchdog 486 00:23:56,160 --> 00:23:58,475 that we have to worry about in this other organization. 487 00:24:13,150 --> 00:24:16,450 So another nice property of this client service organization 488 00:24:16,450 --> 00:24:19,140 is that so far we've presented it 489 00:24:19,140 --> 00:24:21,440 in the context of the client and the service 490 00:24:21,440 --> 00:24:23,490 being modularized from each other, 491 00:24:23,490 --> 00:24:28,390 and we've enforced modularity to the client and the service. 492 00:24:28,390 --> 00:24:30,500 But in fact, there is another nice property to it, 493 00:24:30,500 --> 00:24:34,120 which is that a client service organization allows 494 00:24:34,120 --> 00:24:38,920 us to design modules and design systems where clients get 495 00:24:38,920 --> 00:24:41,530 modularized from each other. 496 00:24:41,530 --> 00:24:44,840 We can achieve soft modularity by protecting clients 497 00:24:44,840 --> 00:24:56,080 from each other. 498 00:24:56,080 --> 00:24:59,880 The idea here is that if you have many clients all of which 499 00:24:59,880 --> 00:25:03,480 want to use a given service, for example, there's 500 00:25:03,480 --> 00:25:07,080 a service that's, let's say, implemented by a bank 501 00:25:07,080 --> 00:25:09,934 and what it does is it's the service that 502 00:25:09,934 --> 00:25:11,350 deals with managing your accounts, 503 00:25:11,350 --> 00:25:13,040 and you can move money between accounts, 504 00:25:13,040 --> 00:25:16,720 and it will tell you your account balance and so on. 505 00:25:16,720 --> 00:25:18,700 You can implement that as one service, 506 00:25:18,700 --> 00:25:22,650 and many, many clients can share the same service. 507 00:25:22,650 --> 00:25:25,090 Now, all of the clients trust the service because, I mean, 508 00:25:25,090 --> 00:25:27,950 if you are a customer of a bank, and you are using your browser 509 00:25:27,950 --> 00:25:30,530 to look for your account balance, that means 510 00:25:30,530 --> 00:25:31,950 you sort of trust the bank. 511 00:25:31,950 --> 00:25:34,470 And all the clients trust the service. 512 00:25:34,470 --> 00:25:38,150 But the clients sure don't trust each other. 513 00:25:38,150 --> 00:25:39,960 And the nice thing about this organization 514 00:25:39,960 --> 00:25:44,360 is that you can use the service in the form of an intermediary 515 00:25:44,360 --> 00:25:50,320 that allows the clients to be separated from each other, each 516 00:25:50,320 --> 00:25:51,580 of which can use the service. 517 00:25:51,580 --> 00:25:53,580 But the clients don't have to trust each other, 518 00:25:53,580 --> 00:25:56,460 and clients don't really have to know 519 00:25:56,460 --> 00:25:58,950 about each other's information. 520 00:25:58,950 --> 00:26:03,280 And this idea of using a service to modularize clients 521 00:26:03,280 --> 00:26:06,750 from each other is called a trusted intermediary. 522 00:26:06,750 --> 00:26:13,180 There is many examples of trusted intermediaries 523 00:26:13,180 --> 00:26:15,690 that we'll see in this course. 524 00:26:15,690 --> 00:26:18,350 In fact, tomorrow's recitation on the X Windows system 525 00:26:18,350 --> 00:26:20,800 has a system where your computer screen 526 00:26:20,800 --> 00:26:26,120 is going to be managed by a service called by the X Windows 527 00:26:26,120 --> 00:26:26,760 system. 528 00:26:26,760 --> 00:26:29,343 And there are many clients that are going to use that service. 529 00:26:29,343 --> 00:26:32,440 And the clients don't actually trust each other. 530 00:26:32,440 --> 00:26:36,040 They want to get modularized away from each other. 531 00:26:36,040 --> 00:26:39,644 And the X Windows system as a trusted intermediary 532 00:26:39,644 --> 00:26:40,310 deals with that. 533 00:26:40,310 --> 00:26:42,680 It managed this resource -- your display, 534 00:26:42,680 --> 00:26:47,035 and it arranges for the clients to be designed each independent 535 00:26:47,035 --> 00:26:47,660 from the other. 536 00:26:50,190 --> 00:26:53,540 And in general, we are going to see in the next few lectures, 537 00:26:53,540 --> 00:26:56,570 many examples of the operating system being a trusted 538 00:26:56,570 --> 00:27:00,800 intermediary, arranging for many different clients 539 00:27:00,800 --> 00:27:03,720 to use some resource on your computer like the processor 540 00:27:03,720 --> 00:27:05,760 or the memory or the disk. 541 00:27:05,760 --> 00:27:08,340 And our architecture for the operating 542 00:27:08,340 --> 00:27:11,225 is going to end up being in the form of these trusted 543 00:27:11,225 --> 00:27:11,850 intermediaries. 544 00:27:29,940 --> 00:27:33,850 So, so far we've seen what client service organization 545 00:27:33,850 --> 00:27:34,350 means. 546 00:27:34,350 --> 00:27:36,141 It means you have a client and the service, 547 00:27:36,141 --> 00:27:37,710 and they communicate with messages 548 00:27:37,710 --> 00:27:39,800 using the communication path abstraction 549 00:27:39,800 --> 00:27:41,420 of send and receive. 550 00:27:41,420 --> 00:27:44,612 And we've seen some properties of client service organization. 551 00:27:44,612 --> 00:27:46,070 But I haven't actually told you how 552 00:27:46,070 --> 00:27:48,110 to implement any of this stuff. 553 00:27:48,110 --> 00:27:51,480 And so that's what we're going to do the rest of today. 554 00:27:51,480 --> 00:27:53,130 And in fact, we are going to continue 555 00:27:53,130 --> 00:27:54,900 with different ways of implementing 556 00:27:54,900 --> 00:27:58,450 various forms of client service many times in the course. 557 00:28:15,910 --> 00:28:19,280 So there are many ways to implement client service 558 00:28:19,280 --> 00:28:20,000 organization. 559 00:28:20,000 --> 00:28:22,960 And all of them have to do with, all of them 560 00:28:22,960 --> 00:28:26,060 involved different ways in which messages are sent 561 00:28:26,060 --> 00:28:28,830 between client and service. 562 00:28:28,830 --> 00:28:31,560 A common way, and a pretty standard way, 563 00:28:31,560 --> 00:28:34,800 of implementing it is something called a remote procedure call. 564 00:28:43,620 --> 00:28:45,660 There are many examples of remote procedure 565 00:28:45,660 --> 00:28:46,360 called systems. 566 00:28:46,360 --> 00:28:49,929 I mean, one of the most common ones 567 00:28:49,929 --> 00:28:51,970 is something called the Sun Remote Procedure Call 568 00:28:51,970 --> 00:28:54,090 system, or Sun RPC. 569 00:28:54,090 --> 00:28:56,120 That's one example. 570 00:28:56,120 --> 00:28:58,440 There are many other examples as well. 571 00:28:58,440 --> 00:29:03,160 A more modern example which some of you may have heard of 572 00:29:03,160 --> 00:29:06,180 is a relatively new system, about five years old, 573 00:29:06,180 --> 00:29:07,630 called XML RPC. 574 00:29:11,670 --> 00:29:15,090 So if you've heard of buzzwords like Web services 575 00:29:15,090 --> 00:29:18,110 in business-to-business interactions, 576 00:29:18,110 --> 00:29:21,460 or business-to-business applications, 577 00:29:21,460 --> 00:29:24,410 these things use something called XML RPC. 578 00:29:24,410 --> 00:29:28,730 And, there is a lot of different three letter acronyms and four 579 00:29:28,730 --> 00:29:30,020 letter acronyms. 580 00:29:30,020 --> 00:29:32,140 This has led to something called SOAP, 581 00:29:32,140 --> 00:29:37,750 which stands for the Simple Object Access Protocol. 582 00:29:37,750 --> 00:29:41,390 So there are many different ways of implementing RPC systems. 583 00:29:41,390 --> 00:29:46,700 And until last year or a couple of years 584 00:29:46,700 --> 00:29:48,640 ago, we used to talk about Sun RPC 585 00:29:48,640 --> 00:29:50,450 as an example in this class. 586 00:29:50,450 --> 00:29:52,290 But I decided that's so 20th century. 587 00:29:52,290 --> 00:29:56,230 So we're going to talk about XML RPC today. 588 00:29:56,230 --> 00:29:59,560 It has a property that's much more inefficient, 589 00:29:59,560 --> 00:30:01,724 but that's sort of keeping with the fact 590 00:30:01,724 --> 00:30:03,140 that computers have become faster. 591 00:30:03,140 --> 00:30:06,030 We don't have to worry in many cases about efficiency. 592 00:30:06,030 --> 00:30:10,350 So we are going to talk a little bit about how XML RPC works. 593 00:30:14,450 --> 00:30:22,200 So let me first show you what a client written what 594 00:30:22,200 --> 00:30:24,630 this kind of RPC looks like. 595 00:30:24,630 --> 00:30:28,090 It's going to show you a code snippet. 596 00:30:32,620 --> 00:30:43,320 All right, I had to work hard to make sure it would fit on this. 597 00:30:43,320 --> 00:30:47,020 OK, all right, the way this thing works 598 00:30:47,020 --> 00:30:50,420 is actually very, very simple. 599 00:30:50,420 --> 00:30:55,360 This uses something called XML RPC Library for Java that was 600 00:30:55,360 --> 00:30:58,520 written by the Apache people. 601 00:30:58,520 --> 00:31:00,640 And once you incorporate that library, 602 00:31:00,640 --> 00:31:03,020 your program becomes completely easy. 603 00:31:03,020 --> 00:31:04,620 So let me just walk you through this. 604 00:31:04,620 --> 00:31:06,780 The high level idea here is that it's 605 00:31:06,780 --> 00:31:10,780 transferring money from one account to the other 606 00:31:10,780 --> 00:31:14,440 through a service that's run by the bank. 607 00:31:14,440 --> 00:31:17,320 So, the first line of this thing here 608 00:31:17,320 --> 00:31:21,455 creates an XML RPC object, an XML RPC client object. 609 00:31:21,455 --> 00:31:23,830 And what you give it is actually the name of the service. 610 00:31:23,830 --> 00:31:25,996 So somebody has to tell you the name of the service. 611 00:31:25,996 --> 00:31:28,550 And I don't want to get into the details of everything here, 612 00:31:28,550 --> 00:31:31,010 but the basic idea is your backname.com 613 00:31:31,010 --> 00:31:34,570 colon 8080 is the name, the DNS name at which the service runs 614 00:31:34,570 --> 00:31:35,510 and the port. 615 00:31:35,510 --> 00:31:37,200 The thing about XML RPC is that it 616 00:31:37,200 --> 00:31:39,330 runs over HTTP which is what you use 617 00:31:39,330 --> 00:31:42,260 to transfer objects on the Web. 618 00:31:42,260 --> 00:31:44,430 And underneath, we talk about how it's implemented; 619 00:31:44,430 --> 00:31:48,040 underneath this is implemented using a standard method in HTTP 620 00:31:48,040 --> 00:31:50,050 called a POST which allows, normally 621 00:31:50,050 --> 00:31:51,990 HTTP has a GET where you retrieve 622 00:31:51,990 --> 00:31:53,700 But it also has a POST that many of you 623 00:31:53,700 --> 00:31:55,490 are familiar with where the client can 624 00:31:55,490 --> 00:31:57,810 push some stuff to the server. 625 00:31:57,810 --> 00:32:01,752 And it just uses POST method. 626 00:32:01,752 --> 00:32:02,960 What's going on is very easy? 627 00:32:02,960 --> 00:32:05,310 You create a vector of parameters, 628 00:32:05,310 --> 00:32:07,610 and you fill that vector in with, 629 00:32:07,610 --> 00:32:09,620 in this case, your account number. 630 00:32:09,620 --> 00:32:13,720 And let's say here the idea is this sort of thing 631 00:32:13,720 --> 00:32:16,280 is very popular in big companies like Ford or Cisco, 632 00:32:16,280 --> 00:32:18,110 which have thousands of suppliers. 633 00:32:18,110 --> 00:32:21,800 And, they never actually maintain a lot 634 00:32:21,800 --> 00:32:23,944 of inventory of their own. 635 00:32:23,944 --> 00:32:25,860 They're always trying to figure out the latest 636 00:32:25,860 --> 00:32:27,190 cost of any of their supplies. 637 00:32:27,190 --> 00:32:29,550 And they are using this Web service like interface. 638 00:32:29,550 --> 00:32:32,702 In fact, this is also called a Web service interface 639 00:32:32,702 --> 00:32:34,160 to communicate with their suppliers 640 00:32:34,160 --> 00:32:38,040 to always have the latest info whether their suppliers have 641 00:32:38,040 --> 00:32:40,452 any given item in stock, and how much it costs and so on. 642 00:32:40,452 --> 00:32:42,660 So, let's pretend you have done that in your company, 643 00:32:42,660 --> 00:32:45,220 and you are trying to pay off, you 644 00:32:45,220 --> 00:32:47,410 are taking your suppliers' account number 645 00:32:47,410 --> 00:32:49,200 and pay some money to him, OK? 646 00:32:49,200 --> 00:32:54,750 So in this case, whatever, dollars is that argument. 647 00:32:54,750 --> 00:32:55,840 So you create parameters. 648 00:32:55,840 --> 00:32:58,970 And all you do at the end is you use these XML RPC client 649 00:32:58,970 --> 00:33:03,800 objects, and invoke a method it presents to you called execute. 650 00:33:03,800 --> 00:33:05,600 And you give it two arguments. 651 00:33:05,600 --> 00:33:07,255 The second argument is the parameters. 652 00:33:07,255 --> 00:33:09,380 And the first argument is the name of the procedure 653 00:33:09,380 --> 00:33:12,050 that you wish to run on the service. 654 00:33:12,050 --> 00:33:15,590 OK, that's in this case called MoneyTransfer. 655 00:33:15,590 --> 00:33:17,830 So, corresponding to this, somewhat longer 656 00:33:17,830 --> 00:33:20,570 is a piece of code running on the service which implements 657 00:33:20,570 --> 00:33:25,610 the server side of it, which basically obtains 658 00:33:25,610 --> 00:33:33,130 [SOUND OFF/THEN ON] calls an object that will un-marshall 659 00:33:33,130 --> 00:33:35,800 the arguments, and then it will execute money transfer, 660 00:33:35,800 --> 00:33:40,310 both of which [SOUND There is very little that actually 661 00:33:40,310 --> 00:33:41,524 has to run on the service. 662 00:33:41,524 --> 00:33:43,190 It's just a little bit longer than this. 663 00:33:45,700 --> 00:33:48,685 Now, this line here is important. 664 00:33:48,685 --> 00:33:50,560 That's the line on which you get your result. 665 00:33:50,560 --> 00:33:52,530 And this gives the result as a string. 666 00:33:52,530 --> 00:33:55,300 If I tell you that I finished transferring 667 00:33:55,300 --> 00:33:59,160 X dollars from this account to that account, or if I tell you 668 00:33:59,160 --> 00:34:02,080 I couldn't transfer, and there was some kind of an error, 669 00:34:02,080 --> 00:34:06,210 or you might actually not get any answer, in which case 670 00:34:06,210 --> 00:34:10,570 the underlying library that implements this procedure call 671 00:34:10,570 --> 00:34:13,580 would throw an exception your code has to deal with. 672 00:34:13,580 --> 00:34:16,120 And how you deal with it is a little tricky because you 673 00:34:16,120 --> 00:34:17,934 don't, and you'll see this in a moment, 674 00:34:17,934 --> 00:34:19,350 you don't quite know what happened 675 00:34:19,350 --> 00:34:21,389 when you didn't get an answer back 676 00:34:21,389 --> 00:34:25,639 from the You don't know if this actually got your transfer 677 00:34:25,639 --> 00:34:30,159 request and crashed after that. 678 00:34:30,159 --> 00:34:31,500 And, it got the request. 679 00:34:31,500 --> 00:34:33,400 It actually implemented the transfer and then crashed. 680 00:34:33,400 --> 00:34:35,000 It just couldn't send your response back. 681 00:34:35,000 --> 00:34:36,749 So, you're not quite sure whether you need 682 00:34:36,749 --> 00:34:38,900 to retry the request or not. 683 00:34:38,900 --> 00:34:41,070 You will actually see how to deal 684 00:34:41,070 --> 00:34:45,239 with this in a few minutes. 685 00:34:45,239 --> 00:34:47,699 Now, there's one thing that's really 686 00:34:47,699 --> 00:34:49,850 important about this line of code. 687 00:34:49,850 --> 00:34:54,650 This xmlrpc.execute( "MoneyTransfer") block, 688 00:34:54,650 --> 00:34:57,750 that line of code actually is not something that runs 689 00:34:57,750 --> 00:34:59,590 on the service. 690 00:34:59,590 --> 00:35:02,000 OK, it's a local procedure. 691 00:35:02,000 --> 00:35:05,150 xmlprc.execute() is a local procedure. 692 00:35:05,150 --> 00:35:10,110 OK, and that procedure is an example of something called 693 00:35:10,110 --> 00:35:15,205 a stub because what it is, is a stub that to this caller 694 00:35:15,205 --> 00:35:17,580 fakes out the fact that there's a service somewhere else. 695 00:35:17,580 --> 00:35:20,330 I mean, it prevents the caller from having 696 00:35:20,330 --> 00:35:22,640 to deal with 15 arguments and putting it in the message 697 00:35:22,640 --> 00:35:24,440 and sending it to the other side. 698 00:35:24,440 --> 00:35:26,800 The caller just calls it over the procedure, 699 00:35:26,800 --> 00:35:29,910 giving it suitable arguments that pinch for this 700 00:35:29,910 --> 00:35:31,700 function now to do the work of sending 701 00:35:31,700 --> 00:35:33,080 a message across the network. 702 00:35:33,080 --> 00:35:36,360 But this is a local call. 703 00:35:36,360 --> 00:35:38,030 So, what happens underneath? 704 00:35:38,030 --> 00:35:41,400 Underneath in the library, once you call xmlrpc.execute() 705 00:35:41,400 --> 00:35:43,690 in this example, somebody does work. 706 00:35:43,690 --> 00:35:46,540 That library does the work of taking the different arguments 707 00:35:46,540 --> 00:35:49,440 that have been presented to it and converting them 708 00:35:49,440 --> 00:35:52,930 into a message, marshalling all of the stuff into a message, 709 00:35:52,930 --> 00:35:55,220 and then shipping that message off to the server. 710 00:35:55,220 --> 00:35:57,761 That has to be going to some kind of a format on the Fly, 711 00:35:57,761 --> 00:35:58,260 right? 712 00:35:58,260 --> 00:36:00,134 Ultimately on this wire connecting the client 713 00:36:00,134 --> 00:36:01,700 to the service, there's format. 714 00:36:01,700 --> 00:36:04,670 And I already mentioned that this runs on top of HTTP. 715 00:36:04,670 --> 00:36:08,610 And so we can actually look at what that looks like. 716 00:36:12,750 --> 00:36:20,520 OK, so POST here is the method that you use in HTTP. 717 00:36:20,520 --> 00:36:24,860 The /RPC2 is actually the same thing that was used in, if you 718 00:36:24,860 --> 00:36:28,890 remember in the previous screenshot, 719 00:36:28,890 --> 00:36:34,770 when we did the new call to get a new XML RPC client, 720 00:36:34,770 --> 00:36:36,980 we gave it a server name and a port number. 721 00:36:36,980 --> 00:36:38,970 But we also gave it something called RPC2. 722 00:36:38,970 --> 00:36:41,600 Now, that's just like a file on the other side. 723 00:36:41,600 --> 00:36:44,140 It says there are many different RPC programs running 724 00:36:44,140 --> 00:36:45,060 on your service. 725 00:36:45,060 --> 00:36:46,590 And I want RPC2 to run. 726 00:36:46,590 --> 00:36:50,610 I mean, I could have named it anything I wanted. 727 00:36:50,610 --> 00:36:54,360 And that's a lot like giving a file name on a URL. 728 00:36:54,360 --> 00:36:56,887 And then, you go on. 729 00:36:56,887 --> 00:36:57,970 You give it the host name. 730 00:36:57,970 --> 00:36:59,900 This is a lot like an HTTP header. 731 00:36:59,900 --> 00:37:04,900 The interesting new stuff here is in the XML arguments. 732 00:37:04,900 --> 00:37:06,590 But those were not familiar with XML. 733 00:37:06,590 --> 00:37:08,950 It's just a method, a way of sending 734 00:37:08,950 --> 00:37:11,520 things that have attributes and values associated with them. 735 00:37:11,520 --> 00:37:15,140 So, every method has the format that it's 736 00:37:15,140 --> 00:37:16,610 attributes and values, and they can 737 00:37:16,610 --> 00:37:18,520 be nested within each other. 738 00:37:18,520 --> 00:37:20,350 The only interesting thing that's here, 739 00:37:20,350 --> 00:37:23,750 this particular XML RPC system supports a few different data 740 00:37:23,750 --> 00:37:24,380 formats. 741 00:37:24,380 --> 00:37:26,970 You can do integers, and characters, and strings, 742 00:37:26,970 --> 00:37:30,410 and doubles, and floats, and a few different things like that. 743 00:37:30,410 --> 00:37:32,640 And I thought it just means that the 32 bit integer, 744 00:37:32,640 --> 00:37:36,570 and you can take numbers that sum up your account number, 745 00:37:36,570 --> 00:37:39,520 your supplier's account number, and the amount of money 746 00:37:39,520 --> 00:37:41,769 that you want to transfer. 747 00:37:41,769 --> 00:37:43,310 The good thing is that all this stuff 748 00:37:43,310 --> 00:37:45,580 has gone underneath the covers, and you don't actually 749 00:37:45,580 --> 00:37:47,180 have to deal with it if you are writing the client 750 00:37:47,180 --> 00:37:48,150 or you are writing the service. 751 00:37:48,150 --> 00:37:49,750 All this work happens underneath. 752 00:37:49,750 --> 00:37:54,150 So, it greatly simplifies your ability to take, 753 00:37:54,150 --> 00:37:56,760 implement client service programs 754 00:37:56,760 --> 00:38:08,950 with clients and services being separated from one another. 755 00:38:08,950 --> 00:38:10,980 OK. 756 00:38:10,980 --> 00:38:12,480 So, so far, we've made it look a lot 757 00:38:12,480 --> 00:38:14,771 except for this little timer that you have to maintain. 758 00:38:14,771 --> 00:38:20,660 We've made it look a lot like a remote procedure call, 759 00:38:20,660 --> 00:38:21,786 it's like a procedure call. 760 00:38:21,786 --> 00:38:23,576 In fact, the code here, the only difference 761 00:38:23,576 --> 00:38:25,010 is you replace what was previously 762 00:38:25,010 --> 00:38:27,610 what would have been one big transfer with arguments 763 00:38:27,610 --> 00:38:30,576 we replace with a stub call, taking 764 00:38:30,576 --> 00:38:31,950 the name of the procedure we want 765 00:38:31,950 --> 00:38:33,740 to run on the service [NOISE OBSCURES]. 766 00:38:33,740 --> 00:38:36,930 So, it looks a lot like a procedure call. 767 00:38:36,930 --> 00:38:38,680 That actually is a pretty deceptive thing. 768 00:38:38,680 --> 00:38:40,930 And in fact, a hint at that is you 769 00:38:40,930 --> 00:38:43,870 can get at the bottom of this thing up there, 770 00:38:43,870 --> 00:38:47,540 there is a light that says you have 771 00:38:47,540 --> 00:38:50,720 to deal with XML RPC exception. 772 00:38:50,720 --> 00:38:53,620 And that's the kind of exception you get when the underlying RPC 773 00:38:53,620 --> 00:38:55,650 library decides that it hasn't heard 774 00:38:55,650 --> 00:38:58,460 an answer from the service in a while, it throws an exception. 775 00:38:58,460 --> 00:39:00,460 And your code has to deal with it. 776 00:39:00,460 --> 00:39:02,960 You are never going to get that kind of exception 777 00:39:02,960 --> 00:39:04,210 from a regular procedure call. 778 00:39:04,210 --> 00:39:06,150 I didn't hear back from the caller 779 00:39:06,150 --> 00:39:08,080 or from the callee to do something. 780 00:39:08,080 --> 00:39:13,120 See, that's a new exception mode that you didn't previously 781 00:39:13,120 --> 00:39:13,920 have to deal with. 782 00:39:13,920 --> 00:39:16,840 I mean, you have to deal with other kinds of exceptions 783 00:39:16,840 --> 00:39:19,160 but not this one. 784 00:39:19,160 --> 00:39:26,807 So, an RPC is not the same as a procedure call. 785 00:39:26,807 --> 00:39:28,390 And in fact, it's a little unfortunate 786 00:39:28,390 --> 00:39:28,640 that, for several reasons, we are stuck a little with a name 787 00:39:28,640 --> 00:39:29,610 procedure call. 788 00:39:29,610 --> 00:39:30,250 In fact, increasingly more and more RPC systems 789 00:39:30,250 --> 00:39:30,330 don't look like procedure calls at all 790 00:39:30,330 --> 00:39:32,270 in terms of the semantics. 791 00:39:32,270 --> 00:39:36,240 But we were so stuck with the name 792 00:39:36,240 --> 00:39:40,700 that people continue to have various kinds of procedure 793 00:39:40,700 --> 00:39:45,160 calls, and they used the same name for it. 794 00:39:45,160 --> 00:39:49,620 And the first main difference arises from the fact 795 00:39:49,620 --> 00:39:54,570 that there is no fate sharing between client and service. 796 00:39:54,570 --> 00:39:58,540 If the service crashes, the client doesn't crash. 797 00:39:58,540 --> 00:40:00,960 Already you have a big difference 798 00:40:00,960 --> 00:40:05,150 between a regular procedure call. 799 00:40:05,150 --> 00:40:08,320 And previously I presented this as an advantage 800 00:40:08,320 --> 00:40:11,450 because if you have fate sharing, then 801 00:40:11,450 --> 00:40:14,920 this caller is always at the mercy of the callee. 802 00:40:14,920 --> 00:40:16,580 But because you have no fate sharing, 803 00:40:16,580 --> 00:40:19,317 you have other problems to deal with. 804 00:40:19,317 --> 00:40:21,400 And in particular, all of these stem from the fact 805 00:40:21,400 --> 00:40:25,050 that it's extremely hard to distinguish between a failure 806 00:40:25,050 --> 00:40:27,570 versus extremely slow. 807 00:40:34,590 --> 00:40:36,720 And it will turn out that we revisit this 808 00:40:36,720 --> 00:40:38,020 over and over again. 809 00:40:38,020 --> 00:40:40,900 We'll talk about networks and reliable concentration 810 00:40:40,900 --> 00:40:42,640 over networks and deal with it, and then 811 00:40:42,640 --> 00:40:44,410 we're going to talk about fall tolerance, 812 00:40:44,410 --> 00:40:47,415 and we're going to talk about an idea for [NOISE OBSCURES], 813 00:40:47,415 --> 00:40:49,540 and then we're going to talk about something called 814 00:40:49,540 --> 00:40:50,322 transactions. 815 00:40:50,322 --> 00:40:52,280 And they're all going to deal with this problem 816 00:40:52,280 --> 00:40:55,150 that it's going to be very hard for us to tell, 817 00:40:55,150 --> 00:40:57,240 when you ask somebody to do a piece of work, 818 00:40:57,240 --> 00:41:00,130 whether they did it fully or did nothing. 819 00:41:00,130 --> 00:41:03,470 OK, and this is going to be a repeated theme, 820 00:41:03,470 --> 00:41:06,320 a theme that is going to repeat in the course. 821 00:41:06,320 --> 00:41:11,020 But to complicate why this is hard, 822 00:41:11,020 --> 00:41:13,050 let me say three possible things that 823 00:41:13,050 --> 00:41:15,680 could happen when you have a client talk to service 824 00:41:15,680 --> 00:41:20,200 and what kind of semantics you want from a client They all 825 00:41:20,200 --> 00:41:23,170 stem from the fact that this is extremely hard to determine. 826 00:41:23,170 --> 00:41:25,840 The first semantics that you might want 827 00:41:25,840 --> 00:41:27,360 is the idea semantic. 828 00:41:27,360 --> 00:41:31,560 The client talks to the service, and either the service answers 829 00:41:31,560 --> 00:41:33,500 with a response or it doesn't. 830 00:41:33,500 --> 00:41:36,840 OK, and that's something called exactly-once semantics. 831 00:41:40,750 --> 00:41:43,160 So in this example here, underneath the library, 832 00:41:43,160 --> 00:41:44,040 it may time out. 833 00:41:44,040 --> 00:41:45,370 And it may wish to retransmit. 834 00:41:45,370 --> 00:41:47,890 Or it may wish to throw an exception at the caller. 835 00:41:47,890 --> 00:41:51,670 The client may want to send this again. 836 00:41:51,670 --> 00:41:55,160 But in an ideal case, you want exactly 837 00:41:55,160 --> 00:41:57,270 once this amount of money to be moved from bank 838 00:41:57,270 --> 00:41:58,980 account one to bank account two, right? 839 00:41:58,980 --> 00:42:01,350 You certainly don't want your amount of money 840 00:42:01,350 --> 00:42:03,770 to be moved twice to your supplier. 841 00:42:03,770 --> 00:42:06,740 The term of this is ideal, and it's 842 00:42:06,740 --> 00:42:09,300 going to be pretty difficult, and extremely hard, 843 00:42:09,300 --> 00:42:12,310 to achieve exactly-once semantics. 844 00:42:12,310 --> 00:42:14,847 And, we're going to talk about different methods 845 00:42:14,847 --> 00:42:15,430 in the course. 846 00:42:15,430 --> 00:42:17,704 This is not an easy problem at all. 847 00:42:17,704 --> 00:42:19,870 It stems from the fact that it is very hard to know. 848 00:42:22,610 --> 00:42:24,100 So, you might give up a little bit 849 00:42:24,100 --> 00:42:27,700 and say, OK, I can't really get exactly-once semantics 850 00:42:27,700 --> 00:42:28,660 very easily. 851 00:42:28,660 --> 00:42:31,200 But let me try for at least once. 852 00:42:34,100 --> 00:42:38,480 So what this means is the client will keep retrying or the 853 00:42:38,480 --> 00:42:39,930 the library will keep retrying. 854 00:42:39,930 --> 00:42:41,900 And you can decompose it in either way 855 00:42:41,900 --> 00:42:45,960 until it is sure that this call succeeded at least once. 856 00:42:45,960 --> 00:42:49,640 Now, it might have succeeded more than once 857 00:42:49,640 --> 00:42:51,494 because the service is very slow. 858 00:42:51,494 --> 00:42:52,410 And then it times out. 859 00:42:52,410 --> 00:42:54,618 You try it again, the service says, oh, OK, I see it; 860 00:42:54,618 --> 00:42:55,810 I must not do it again. 861 00:42:55,810 --> 00:42:58,610 But, it's at least once, OK? 862 00:42:58,610 --> 00:43:00,820 Now, at least once is not nice semantics 863 00:43:00,820 --> 00:43:03,240 that you're using at least one semantics in your code 864 00:43:03,240 --> 00:43:06,540 here, right, because your supplier might end up with $7 865 00:43:06,540 --> 00:43:08,480 million instead of $1 million. 866 00:43:08,480 --> 00:43:10,410 But at least once is OK if the service 867 00:43:10,410 --> 00:43:14,220 has some kind of semantic called idem-potent semantics. 868 00:43:17,990 --> 00:43:21,710 What that means is that when you do an operation more than once, 869 00:43:21,710 --> 00:43:24,860 the answers are the same as at-least-once. 870 00:43:24,860 --> 00:43:28,070 A simple example of this was the transfer of money, 871 00:43:28,070 --> 00:43:30,440 but you checking your bank account 872 00:43:30,440 --> 00:43:33,317 It doesn't really matter that you do it a hundred times. 873 00:43:33,317 --> 00:43:35,900 As long as one of them succeeds and you get your bank balance, 874 00:43:35,900 --> 00:43:36,350 you are fine. 875 00:43:36,350 --> 00:43:37,920 I mean, doing it seven times does not really 876 00:43:37,920 --> 00:43:40,570 change anything; it does not move extra money anywhere else. 877 00:43:40,570 --> 00:43:43,347 So that's an example of an idem-potent action, 878 00:43:43,347 --> 00:43:45,430 which works out well with at-least-once semantics. 879 00:43:49,910 --> 00:43:52,440 And at-least-once semantics is much easier 880 00:43:52,440 --> 00:43:58,400 to obtain than exactly-once semantics. 881 00:43:58,400 --> 00:44:03,430 And the third kind of semantics is something converse: 882 00:44:03,430 --> 00:44:06,720 most-once semantics. 883 00:44:06,720 --> 00:44:08,420 That means zero or more times. 884 00:44:11,290 --> 00:44:13,750 And here, the challenge is really 885 00:44:13,750 --> 00:44:17,740 figuring out if it really worked at least once around. 886 00:44:17,740 --> 00:44:19,120 I mean, I pushed once or not. 887 00:44:19,120 --> 00:44:23,154 So, if you don't get a response back, then you time out. 888 00:44:23,154 --> 00:44:25,070 And it might be that it didn't succeed at all. 889 00:44:25,070 --> 00:44:26,070 And you say that's fine. 890 00:44:26,070 --> 00:44:27,460 I'll deal with it separately. 891 00:44:27,460 --> 00:44:30,286 And if you get a response back, then you know that it worked. 892 00:44:30,286 --> 00:44:32,410 It turns out, even that is going to be a little bit 893 00:44:32,410 --> 00:44:33,243 tricky to implement. 894 00:44:33,243 --> 00:44:35,320 But these kinds of semantics you could 895 00:44:35,320 --> 00:44:38,480 expect from your RPC system. 896 00:44:38,480 --> 00:44:41,596 Now, actually the first R in most RPC systems like XML RPC 897 00:44:41,596 --> 00:44:43,720 don't really deal with any of this in a particular, 898 00:44:43,720 --> 00:44:45,094 I mean, they don't really provide 899 00:44:45,094 --> 00:44:46,290 any well-defined semantics. 900 00:44:46,290 --> 00:44:48,450 It's usually for the client sitting on top, 901 00:44:48,450 --> 00:44:49,950 and the service is still, they don't 902 00:44:49,950 --> 00:44:51,580 know what kind of semantics they need, 903 00:44:51,580 --> 00:44:54,430 and implement that at a higher layer at least 904 00:44:54,430 --> 00:44:56,820 with most of these standard protocols. 905 00:44:56,820 --> 00:44:58,560 But many of them are well equipped 906 00:44:58,560 --> 00:45:01,710 to deal with at-least-once semantics. 907 00:45:01,710 --> 00:45:04,450 OK, and through the course, there 908 00:45:04,450 --> 00:45:05,840 are different ways in which we'll 909 00:45:05,840 --> 00:45:08,010 accomplish these different goals, 910 00:45:08,010 --> 00:45:15,050 these different semantics that we want from our different RPC 911 00:45:15,050 --> 00:45:16,040 systems. 912 00:45:16,040 --> 00:45:24,010 Now, there's another difference between regular procedure calls 913 00:45:24,010 --> 00:45:26,210 and remote procedure calls, or more 914 00:45:26,210 --> 00:45:29,660 generally from client service. 915 00:45:29,660 --> 00:45:32,310 Remember in the second lecture, I 916 00:45:32,310 --> 00:45:35,050 told you that you can always get more bandwidth, 917 00:45:35,050 --> 00:45:37,526 and you can always get more processing past Moore's law, 918 00:45:37,526 --> 00:45:39,150 but one thing you can't actually change 919 00:45:39,150 --> 00:45:42,320 is the legacy between two computers connected 920 00:45:42,320 --> 00:45:43,850 by a wire connected by a network. 921 00:45:43,850 --> 00:45:46,630 The speed of light doesn't change. 922 00:45:46,630 --> 00:45:49,090 What that means is that with time, 923 00:45:49,090 --> 00:45:51,000 the number of constructions that you can run, 924 00:45:51,000 --> 00:45:53,000 when you have two computers separated by a wire, 925 00:45:53,000 --> 00:45:55,600 there is a certain delay between that no matter what you do. 926 00:45:55,600 --> 00:45:58,280 So there is a certain delay that you do a procedure call that's 927 00:45:58,280 --> 00:45:59,490 a remote procedure call. 928 00:45:59,490 --> 00:46:00,870 It takes a certain delay to send a message 929 00:46:00,870 --> 00:46:01,994 and to get a response back. 930 00:46:01,994 --> 00:46:04,360 Even as computers get faster and faster and faster, 931 00:46:04,360 --> 00:46:06,447 that isn't changing at all. 932 00:46:06,447 --> 00:46:08,530 But the problem is that the number of instructions 933 00:46:08,530 --> 00:46:10,110 you can run but within that duration 934 00:46:10,110 --> 00:46:12,610 is increasing with time because it's a fixed amount of time, 935 00:46:12,610 --> 00:46:14,776 and the number of instructions you could run locally 936 00:46:14,776 --> 00:46:18,430 on the computer increases with time. 937 00:46:18,430 --> 00:46:22,940 So that has led people to be more aggressive about what they 938 00:46:22,940 --> 00:46:24,721 do in a remote procedure call. 939 00:46:24,721 --> 00:46:26,720 What people said is, wait, it doesn't make sense 940 00:46:26,720 --> 00:46:30,380 for a client to issue a procedure call, 941 00:46:30,380 --> 00:46:31,960 relocate to a service, and then just 942 00:46:31,960 --> 00:46:35,490 sit and wait like in a regular procedure call, for the answer. 943 00:46:35,490 --> 00:46:37,810 I mean, I'm just sitting there twiddling my thumbs, 944 00:46:37,810 --> 00:46:41,170 and this thing is that way, and I'm waiting for it to respond. 945 00:46:41,170 --> 00:46:44,290 I could be doing work. 946 00:46:44,290 --> 00:46:51,370 So, that's led people to changing the synchronous model 947 00:46:51,370 --> 00:46:53,680 of RPC, of a procedure call interface 948 00:46:53,680 --> 00:46:56,190 to do something called asynchronous procedure call 949 00:46:56,190 --> 00:46:56,690 interface. 950 00:46:56,690 --> 00:46:59,909 And all the things like XML RPC and its follow-on, 951 00:46:59,909 --> 00:47:01,700 and the difference between SOAP and XML RPC 952 00:47:01,700 --> 00:47:05,950 is that I can understand this, and this builds on XML RPC. 953 00:47:05,950 --> 00:47:11,820 It seems like very few people understand SOAP. 954 00:47:11,820 --> 00:47:14,440 There is a lot of people who have given up 955 00:47:14,440 --> 00:47:16,670 on trying to understand the specification. 956 00:47:16,670 --> 00:47:20,300 But XML RPC turns out to be a really simple seven or ten page 957 00:47:20,300 --> 00:47:22,320 document that's very easy to understand. 958 00:47:22,320 --> 00:47:24,330 A lot of people use it. 959 00:47:24,330 --> 00:47:27,620 But anyway, all these systems support asynchronous RPC. 960 00:47:27,620 --> 00:47:30,380 The idea here is that the client sends 961 00:47:30,380 --> 00:47:33,150 a procedure call indicating a remote request to the service. 962 00:47:33,150 --> 00:47:36,260 And then it goes about doing its work. 963 00:47:36,260 --> 00:47:38,430 When the service responds with an answer, 964 00:47:38,430 --> 00:47:40,580 it responds with not just the answer, but also 965 00:47:40,580 --> 00:47:42,630 something that tells the client which 966 00:47:42,630 --> 00:47:44,760 service request, which procedure caller request 967 00:47:44,760 --> 00:47:47,300 it's responding to. 968 00:47:47,300 --> 00:47:52,050 And when the response comes back, the client can handle it. 969 00:47:52,050 --> 00:47:54,570 Now, the way in which you have to implement this, 970 00:47:54,570 --> 00:47:55,990 or the way you have to design this 971 00:47:55,990 --> 00:47:58,780 is that associated with every procedure call request, 972 00:47:58,780 --> 00:48:00,480 you also have to associate what's 973 00:48:00,480 --> 00:48:03,260 called a handler because you're going 974 00:48:03,260 --> 00:48:05,630 to issue this request to the service 975 00:48:05,630 --> 00:48:07,260 and then go about doing your work. 976 00:48:07,260 --> 00:48:11,360 When the answer comes back, the RPC library underneath, 977 00:48:11,360 --> 00:48:14,141 the communication library has to know: who gets this answer? 978 00:48:14,141 --> 00:48:16,390 Because you might have to a sheet of many such service 979 00:48:16,390 --> 00:48:17,160 requests. 980 00:48:17,160 --> 00:48:19,000 So who gets this answer? 981 00:48:19,000 --> 00:48:21,770 So you associate with every request 982 00:48:21,770 --> 00:48:23,940 a callback, a handler, which then is called back. 983 00:48:23,940 --> 00:48:26,550 And that handler runs, dealing with the answer that 984 00:48:26,550 --> 00:48:27,740 comes back. 985 00:48:27,740 --> 00:48:31,350 And so, that actually allows you to be a little more decoupled 986 00:48:31,350 --> 00:48:33,830 than we were with the remote procedure call; even more 987 00:48:33,830 --> 00:48:34,330 decoupled. 988 00:48:34,330 --> 00:48:36,280 The client services are even more decoupled 989 00:48:36,280 --> 00:48:39,350 because the client is no longer waiting for the service 990 00:48:39,350 --> 00:48:43,270 to return an answer to. 991 00:48:43,270 --> 00:48:46,390 So that's the first way which people have extended it. 992 00:48:46,390 --> 00:48:48,260 The second way in which people have extended 993 00:48:48,260 --> 00:48:51,680 is using this intermediary idea that we talked about 994 00:48:51,680 --> 00:48:55,010 before where the services cross the intermediary. 995 00:48:55,010 --> 00:48:58,250 To use this intermediary idea to actually make 996 00:48:58,250 --> 00:49:02,430 design remote message based communication systems where 997 00:49:02,430 --> 00:49:07,160 the client and service don't actually have to be up 998 00:49:07,160 --> 00:49:09,300 and running at the same time. 999 00:49:09,300 --> 00:49:13,260 So actually, the client could send a request out 1000 00:49:13,260 --> 00:49:14,092 to the service. 1001 00:49:14,092 --> 00:49:16,050 But the service is actually not up and running. 1002 00:49:16,050 --> 00:49:18,000 So, the idea is there is an intermediary that 1003 00:49:18,000 --> 00:49:19,790 acts as a broker on behalf of the service, 1004 00:49:19,790 --> 00:49:20,790 and buffers the message. 1005 00:49:20,790 --> 00:49:20,860 And then, when the service comes out, 1006 00:49:20,860 --> 00:49:20,960 the service knows to pull the message from this intermediary. 1007 00:49:20,960 --> 00:49:21,000 That's buffered messages, correct? 1008 00:49:21,000 --> 00:49:23,416 And then it passes the message, and then pushes the answer 1009 00:49:23,416 --> 00:49:29,690 back to the intermediary, which then 1010 00:49:29,690 --> 00:49:35,059 stores the message to some other intermediary perhaps. 1011 00:49:35,059 --> 00:49:36,850 And then the client knows to get the answer 1012 00:49:36,850 --> 00:49:38,230 from that intermediary. 1013 00:49:38,230 --> 00:49:40,580 So now, we can actually have clients and services 1014 00:49:40,580 --> 00:49:43,330 that interact with each other without actually 1015 00:49:43,330 --> 00:49:45,510 having to be up and running at the same time. 1016 00:49:45,510 --> 00:49:48,030 There are many examples of this, and the notes 1017 00:49:48,030 --> 00:49:50,940 talk about various examples of intermediary communication. 1018 00:49:50,940 --> 00:49:55,520 So the general summary of what we've talked about so far 1019 00:49:55,520 --> 00:49:59,680 is that we looked at different ways of attaining modularity, 1020 00:49:59,680 --> 00:50:02,140 talked about soft modularity last time, 1021 00:50:02,140 --> 00:50:06,150 and today about a particular way of enforcing modularity using 1022 00:50:06,150 --> 00:50:07,740 client service organization. 1023 00:50:07,740 --> 00:50:09,320 And the next few lectures, we are 1024 00:50:09,320 --> 00:50:11,695 going to solve a big weakness of the current system which 1025 00:50:11,695 --> 00:50:13,444 is that you need many different computers. 1026 00:50:13,444 --> 00:50:14,986 So we are going to take these ideas, 1027 00:50:14,986 --> 00:50:16,610 and implement them all on one computer. 1028 00:50:16,610 --> 00:50:18,670 See you next week Tuesday.