 Alright, so today, not doing that, we are talking about inodes, which are the final journey of our file system. So this is what's actually used on Linux and Unix, and it's a lot of fun, and you will see that all your page table knowledge is applicable. So yay, that wasn't a waste. So this is what an inode is. So an inode stores everything about the contents of a file. It's permissions, who owns it, et cetera, et cetera. So all that information is stored on something called an inode. So the inode will have store the mode, which are like the read, write, execute permissions for your file. It will also share which owners are in it, so what user owns a file and what group owns a file, timestamps. So when was this file created, accessed, and modified last, so written to, which it's just sitting in an inode, so that's why no one trusts your timestamps on a file, because you can just modify it, you just write out some new timestamp. So that's typically why profs that know better will not accept it. I think, yeah, some friends of mine tried to pull that, like submit an assignment super late and then change the timestamp to before where it was due. So you can do that, because it's just a field there. Yeah. Did it work? Did it work? I will not disclose that. So would it work in this class? Probably not. Would it work in some other class? Yeah, but sorry, you are in ECE, so you probably won't be able to take benefit of that. So other things it stores are how many blocks the file uses, and then the rest of it is kind of the same idea of that indexed allocation. So there will be a bunch of pointers to blocks contained within the inode. So there will be a lot of direct blocks, so they will point directly to a block on the disk, and there are a lot of them to represent a single, like, small file. So remember when we had index allocation, we put all the pointers on a block, so we could store up to, like, two to the 11 pointers. Well, if all our files are kind of small and only take, like, six blocks, we don't really want to take a disk block to keep track of all the pointers. When there's not that many, we have to keep track of anyways. So inodes will have a few pointers there that point directly to a block, so you don't have to allocate a block just for pointers. And then the single indirect, so there'll be a pointer that represents a single indirect indexed allocation, so that will be the indexed allocation we saw before. So that will point to a block on the disk, and all that block on the disk has is a bunch of pointers that represent the other blocks that that file actually contains, which is exactly an index allocation, which kind of had the idea from page tables. So unlike page tables where you just have three levels, and then we have to go through three levels, well, with inodes, we have a variable number of levels, so that single indirect one will go through one level, and then you can think of the double indirect one as a page table with two levels. So if you access that root pointer for the double indirect, it means you're going to go through two tables, so that pointer will point to a block full of pointers, so there can be two of the eleven of them, and then each of those points to another block that are full of pointers, and then all of those point to the actual blocks. And then to support massive files, there's also a triple indirect, so that will just do exactly like page tables do for three levels. So why they do that is so that they can be efficient for small files and also support large files. You don't want to, you know, if a file is only like a few bytes, you don't want to just do everything triple indirect, in that case, even if your file is like two bytes, you're going to waste one block for level two, one block for level one, one block for level zero, and then a block for the actual contents of the file, which would be like two bytes out of like eight kilobytes maybe, so you would be wasting what's that, like thirty two kilobytes on like an eight byte file or something like that, which would be absolutely terrible. So that's why there's the direct pointer, so if it's small, it doesn't even allocate a block for all the pointers. And then if you have larger files that scales up, so it only uses the number of levels that it actually needs to represent the file. And there's a caveat here that we'll see that very small files can actually store its content directly in the inode itself, which we'll see what that optimization looks like. Yep. Yep. So in this case, say you have a small file that only takes up two blocks. So say the file, the first block of the file is like block, I don't know, a thousand, and the next block is two thousand, well in the direct blocks, the first index there, index zero would be block a thousand, and then index one would be block two thousand. So it'd point directly to it. So those will always be in the inode, but they're one pointer. So if it's a small file, they'll just be null. Yep. So triple indirect is there, so if it's valid, like if it's a pointer to a block, then you know you have to hop through three things, but it can just not be used. Yep. So you access these in order. So like the first few blocks of the file would be direct, and then the next after the direct blocks are out, it would start filling it up single indirect, and then if that's all filled up, it would go to double indirect and then triple if it needs to. So it would fill it in order, because the more levels we have to, the longer it's going to take to access it, because we still have to jump all the levels. So we just use them in order, so small files, we just look directly, and the smaller optimizations, we can actually cheat a little bit and store it in there. Yep. So the inode itself will also be on disk, so there is going to be a part of the disk that just stores inodes, and that will be allocated with like a slab allocator, so there will be a bitmap for inodes, and there will be a pool of inodes that you can take and use. So that will also be on the disk. Yep. So we'll see. We'll start making stuff and screwing around with stuff, but essentially it's the contents of a file are an inode, and names are merely an illusion, we'll see. So instead of a page, it's a block now on the disk. So other than that, it behaves the exact same way, and it's the same idea where we fit as many pointers as we can on a block. So the single indirect is exactly what we saw yesterday, just one block, and then double indirect is just like the page table, so there will be one block full of pointers, and if you follow a pointer, it's just to another block full of pointers, and you're supposed to follow it again. So instead of taking one hop, you take two. And then for triple indirect, you take three hops instead of two, or one or two. Okay, so let's see, because we saw how big our file could be before with just essentially a single indirect, so our maximum file size could only be like, was it 16 megabytes? So let's assume we have an inode now and see how big of a file we can support. So in an inode, this is going to be the numbers that are actually used in Linux, it could move if you create your own kernel or something like that, but these are generally the numbers for an inode. So it will have 12 direct pointers, one single indirect pointer, one double, and one triple. So in total, there will be 15 pointers. And then our disk block size would be eight kilobytes again, so we'll use the same numbers from last lecture, and a pointer again is going to be four bytes. So and I'm assuming nothing else is on the indirect blocks, they just contain pointers. So now we can calculate the maximum file size managed by this block. So we know that each of the blocks can contain two of the 11 pointers. So using that, so here's our two of the 11, so each block size is two of the 13, and a pointer is four bytes, which is two of the two. So we can fit two of the 11 pointers in a single indirect table. So if we want to calculate the number of blocks we can address with an inode, well, we can address 12 of them directly, so those are 12 direct pointers. Two of the 13 is the block size. So with our 12 direct pointers, we can support, we can point up to 12 blocks, and then for single indirect, well, it's one block, so we can point up to two of the 11 things, and then with a double indirect wall, that's two of the 11 to the power of two, because each entry points to another one, which can hold two of the 11. And then similarly, for a triple indirect, it's two of the 11 to the power of three. So instead of adding all these numbers, we can just guesstimate. So the biggest term here is going to be the last term. It is going to be by far the biggest, and it's pretty much going to be about that. So in actuality, you'll be able to support a bit more than this, but it's about that. So it's about to the 11 to the power of three, which we know how to do exponents, so that's two to the 13 things we can point to. So the total number of bytes that a file could be, well, we can have two to the 33 blocks, and each block is two to the 13. So if we multiply those together, we can support a file up to two to the 48, which is 64 terabytes. So that is what inodes use on Linux, so you can have a file up to 64 terabytes and a little bit bigger because we didn't calculate these blocks, so it would be a bit bigger. But unfortunately, if you want to store a 70 terabyte file, you can't use an inode. So we haven't hit those limits yet, but one day. OK, any questions about that? Yeah. Oh, no, sorry. So the mode here, the mode is like the same thing as your open, and it's the permissions of the file. So it's like read, write, execute. So you know we can do chmod, some numbers, it's modifying the mode there. Yeah. Yeah, I'm just talking about how many things can fit on this. So if it's double and direct, I have two to the 11, and then each of them points to something that has two to the 11. And then if it's triple, it's another level. Yep. So you get a file descriptor to that file so that when you read from it, it will actually start accessing the disk. But when you call open, you don't read from it, right? It just kind of sets everything up for you. Yeah. So if there is a file on disk, your file is going to be represented by an inode. The first bit of information, the way to get to like the first byte of the file, it would have to access the first direct block and then see what that's pointing at. And then it would start reading that from disk, and that's the first byte of the file. So your kernel does that for you when you read. So it has to access this structure. Yeah. Yeah. Yeah. Yeah. Yeah. So the point of this too is like usually you might only like read the first few bytes of the file and then decide you don't care about. So that's why it's also used to direct and you don't just straight up go to the like triple even if it's a huge file. Yep. So if you want to access bytes of a data, well the first byte is going to be on the first block. Yeah. Yeah. So you read, you can read in the block to memory from the disk and then it's byte accessible. But with this, typically you can only read them into memory at blocks at a time. And then you do byte accessible things. Okay. So let's see. So let's talk about hard links. So this might dispel some illusions you have. So actually let's do this question. So who wants to tell me if I do something like, so if I do touch to do.txt, so that will create a new file called to do.txt that doesn't have any content on it, right? So to do.txt should reference an inode somehow, right? So if I do stat, stat will tell me information about the file and it's essentially stuff that is on the inode itself. So but we'll see soon that this file is not stored in the inode itself. But all this information would be in the inode. So the size of the file, so it's zero bytes. So it's empty. And then you can see, I'm not lying to you, it also says how many blocks it contains. So this one contains zero blocks because it's empty. Then it says how big a block is and then what type it is and where it is. And then here's the inode. So this is it's inode number. So inodes are a real thing. And then there's this curious links number that we will look at soon. And then here's the access. So this is that mode parameter there. So sometimes they call it different things in this, they call it access. Then who owns the file, what group owns the file, and then all the timestamps here. So access, modify, change, and birth, which is just created. I don't know why they call it birth. And then we have LS, yep. What's the difference between modified and change? I'm not sure. It's kind of weird. And some of the terminology is different. So usually it's just created, modified, and accessed. Don't ask me why this is slightly different. So if we do LS-L, there's some things we are kind of familiar with. So there's the modes there. This is actually the number of things that link to the file and then who owns it and timestamps and stuff like that. So soon we will explore that how inodes connect to actual file names. So a hard link is just a pointer to an inode, and that is what todo.txt is. So within a directory, all of the directory is, is a pair of names to inodes. And that's it. That's all a directory contains. It's just a tuple, like a bunch of tuples of name to inode. That's it. There's no more discussion about that matter. That's all it is. Yep. So a directory itself, yeah, a directory itself is a special inode. So it's a directory inode. And the contents of that will be all of the name inode pairs. So there's actually not that much special about a directory. Yep. How do you translate from a path to an inode? So you would go look up that information from the disk. So from the disk, there is a defined root inode, and that's how you know what inode that is. And the root inode is going to be a directory. So that's where all the names are. And then you just follow it. Nope. Yep. So, yeah. The question is, is there a big table that just has all the files and all their paths? And the answer to that is new. All the, there's a special, a root directory, and that contains a bunch of names to inodes. And then past that, that root directory can contain other directories and other directories that have more names, so on and so forth. Yep. So the file name and then what inode that file should represent, that name. So hardlink points to one inode. So you can actually create multiple hardlinks. So what we can do is we can have todo.txt, and then that would be assigned an inode. We got some long number for us. But we can also create another name that points to that. And then deleting a file doesn't actually delete the contents of an inode. It actually just removes a name, and that's all it does. So let's see that. So two, okay, let's go through the example first. So we'll talk about that. So in here we have todo.txt, it's empty. So I can create a hardlink with just ln. So ln, so I'm going to create a new name that points to the same inode as todo.txt, and I'll call it b.txt. So when I create that, it looks like I have two files, and if I do ls-li, so this column is the inode column, and you can see that they both represent the exact same inode. So both names are the same inode, and then this number is the number of links to that inode. So now there's two things pointing to that inode. So what would happen? If I edit todo.txt, I said hello, oops. So now I have todo.txt, our world's all right, so if I cat todo.txt, what am I going to see? Hello, what about if I cat b.txt? Yeah, because it's pointing to the same inode, so it's going to get the same content to the file because inodes just store all the blocks that the file should represent. So I link them with ln. So all ln does is create a new entry in the directory that points to the same inode as the first argument. So now if I go ahead and I edit b.txt, well that's the same inode as hello.txt, or what I call todo.txt, so I'll edit b. So if I edit b, it's the same story. If I cat todo.txt, well I actually changed the contents of the inode because I changed the data that is in the block. So now if I cat todo.txt, it's the same thing, it's the same content because it's the same underlying storage of that. All names are just ways of getting inodes. There's nothing else special about a name other than it's easier to type a name for you than to type an inode. You'd probably be annoyed if you had to type 1583612 every time you wanted to access that content. But other than that, there's nothing special about names. So in addition to hardlinks, so if you called something a hardlink instead of a link that kind of gives you an idea that there's probably something called a softlink. So what a softlink is, is instead of pointing to an inode, it just points to another name. So it's kind of an additional layer of indirection. So this also leads to some interesting things. So if I have to resolve the file and B is a softlink to todo.txt, well if I want to read that, I have to read B.txt, go figure out what B.txt actually represents and then use that to get the inode and then I can actually finally read the contents of the file. So fun things about these are softlinks just contain a name that they're pointing to. So the name doesn't need to exist, which will give you some interesting errors. And even if it does exist at one point, the name it's pointing to might be deleted later. And unresolvable softlinks will lead to some headaches. So some programs will automatically follow softlinks for you and some won't and will just refuse to run if they see a softlink. Yeah. Yeah, yeah. So the question is if there's so many disadvantages with softlinks, why do I use them for hardlinks instead of hardlinks? So you would use softlinks, one, it's really easy to see what they're pointing to other than just like no one checks inode numbers. And number two is that they can actually break the strict hierarchy of things where you have to have, you know, directories within. So normally when we have a file system, we can't create giant loops, right? So with softlinks, you can create loops if you want to, which is also why they're dangerous to go through. Yeah. So a softlink just points to another name. It can be literally anywhere. Yeah. Softlinks just are to a name. Doesn't matter what that name is. Yeah. Yeah. Yeah. Yep. That's it. Yeah. We can try that. We'll try. Yeah. Are there common softlinks? So there's a lot of softlinks typically, like real web servers will use softlinks. It's typically you have files that represent, you know, a website. So typically you might want to enable and disable a website. So instead of removing that file, you'll enable a site by just creating a softlink to that configuration. And then if you want to remove that file or remove that site from your web server, you just remove the softlink. So sometimes they're easier to deal with with stuff like that or just kind of rename stuff under the hood. So you might, you know, have a directory called Python with like the actual full version name. You might create a softlink to that just called Python 3. And then if you update Python, that one would change, but you could still access it through Python 3 or something like that. So softlinks are useful, but they're kind of a pain if you have to deal with them. Okay. So yeah, let's see an example problem and let's play around with it a little bit. So we already have our hardlink. So we already have our hardlink to the same inode. So b and todo.txt point to the same thing. So I can create a softlink and I will call, oops, I will point to todo.txt. I'll call it c.txt. So now when I look at it, well, I can see here is my simlink. So simlinks another way to say softlink, typically they're used interchangeably. So I've c.txt and you can see it says it points to todo.txt. And it itself is an inode. So there's an inode representing the symbolic link and we can stat it if we want. So it says that the size of the file is eight, which makes sense to do.txt is eight characters. So that's why it's size is eight. And there's a special file type for symbolic links. So that's how the system knows what it is. Yep. Ah, that is a great question. So there's a question is why is it zero blocks when the size is eight? So there is a optimization with simlinks. So typically, simlinks are just going to be names and they're going to be pretty short. So if I look, let's go back. If I look at all of my pointers here, so I'll have 12 direct blocks, one single, one double and one triple. So I'll have 15 pointers here. Each pointer is four bytes. So the total of that is 60 bytes for all the pointers. So the optimization is if it's a simlink and the name it's pointing to is under 60 bytes, it will store the content on the pointers because it knows if it's smaller than 60 bytes, I don't need to grab a block. I can just store the content in the iNote itself. So for that case where to do.txt is only size eight, well, it's just going to store itself in the block in like the pointer data for the blocks. So there'll be eight characters there to do.txt and it will be living right here and take up the space where two pointers would have been since it's eight characters. So that is a fun optimization. So we don't waste block size otherwise, how much internal fragmentation would we have if we just had an eight character file? It'd be eight kilobytes minus eight bytes, the rest of it. We're pretty much wasting eight kilobytes. And then also the maximum length of a file name in a directory is 255 characters. So that is your limit on Linux. So there are limits to everything. Yeah, so if it's a directory, the only difference, whoops, that's not, so if it's a directory, so we can just stat, actually dot's a directory, right? So dot is the current directory. So if I stat dot, you can see that it's just an iNote too, but it's a directory iNote. So nothing else special that and its contents have some format and the format is just name to iNote. That's it, it's just a bunch of tuples. So the file name itself is not stored on the iNote itself. It's just pulling that from the argument I gave it. In this case, it's just to do.txt. Yeah, it's the destination. So c.txt is going to be within the directory and then point to an iNote. And whoops, that's i. So c points to this iNote that has the 15. That iNote is a symbolic link. And it contains that data dot, or sorry, that to do dot txt. And that's, you can think of to do dot txt of the contents of that file. But it's defined that if that file type is symbolic link, the contents of the file is actually a name. Yeah, that is an optimization only for symbolic links. Yeah, symbolic link and soft link are the exact same thing. So it's whoever, depends who you're talking to. Yeah. Yeah, so the question is the soft link permissions are all, it's all permissions. So all that means is you can read and write that soft link. It doesn't change the permissions to what it's pointing to. So even though it has all permissions, it doesn't mean the group or anyone else can write to that file. Because all the symbolic would do is chase the name and then figure out, oh, I have to actually open the iNote that to do dot txt points to. So now if I do this, if I cut c.txt, it kind of looks the same as all the rest of them. I'll see hello, I'll let it be. And this way they all kind of work the same way. And then next step I can do, they're all pointing to the same thing. Then we can see what move does. So move, funnily enough, does not move a single thing. So move is also another lie and remove is a lie. So all move does is rename an entry in a directory. If it's within the same directory, if you're moving it, it only actually moves if you move across directories. But if I'm within the same directory, I can move to do dot txt to something like d dot txt. And if I ls again, well, I can see all I did, it's still pointing to the same iNote. All I did was change the name. So now there's still two things pointing to that iNote. I have d dot txt and b dot txt. But now you'll see something is in red because I broke the soft link. Yeah, they're hard links. Yeah, b and d are hard links so there's no arrow. The arrow is only for soft link because soft link is just everything in directory is a name. And then if it's a soft link, it's name to another name. And then if it's a normal file, it's named to an iNote. Yeah, so in the directory, so if we went further and went into the directory, this directory would contain three names. The directory contains b dot txt, c dot txt and d dot txt. And then within them, b dot txt is this iNote, c dot txt is this iNote, which is actually a sim link. And then d dot txt is this iNote. Yeah, yeah, so LS, so this is LS following it. So LS will, if it's the files of sim link, LS will display what it points to for you because LS is nice like that. Yeah, yeah, so the ln call, like without the dash s, that creates a hard link, so it'll create a new name in the directory that points to the same iNote as whatever the first argument is. Yeah, oh wait, c dot other way around. So if I do that, it's smart enough to, they're both in red. So I just create a circular link there. So to do dot txt points to c dot txt and to do dot txt points to c dot txt. And it's smart enough, smart. So yeah, so this is probably something you haven't ever accounted for in your programs. Well, you guys probably never even think of handling a soft link. But in real programs, you have to handle soft links. So it's your choice. Do I follow it? And then if I do follow it, how many times do I follow it? So whoever wrote cat was a very smart cookie because they stop after a certain level if you create an infant loop. But this is the power of sim links or soft links. I can create an infant loop, but with normal files I can't. I'm not allowed to. Yep, so cat tried to do it and it said too many levels. So I followed, it's gonna have a limit where it will follow sim links to I don't know whatever number. Probably something sane, like, I don't know. What's the sane number? Like eight would be kind of insane too. But it'd be like some low number because otherwise it gets kind of crazy. Yeah, whoever wrote cat, it follows it a specified number of times and if it can't actually find a real file, it gives up. So cat is a bit smarter than us. But that was a cool thing to do. All right, so where are we? Yeah, yeah, you can. You can give it the whole path. Like you want to give it the name or the whole path. Yeah, you can give it whatever name you want. So it's, so the first argument is actually a path. So I could do whatever. I could do dot, dot, dot, I don't know, it doesn't even need to exist like high. Whoops, I didn't call anything. Sorry? For the C is linked to D, sorry. That's what we just did. That's like a circular loop. Yeah, so it just follows them. But then if there are real files, it's just gonna read that I node, whatever's on that I node, it's done. So yeah, it doesn't carry. Yeah, or well, I can create a loop if the symbolic link just goes up and then I follow it to myself again. So you can create some recursive cases with it. Yeah. So this, like if I do this or wherever it is, was it like this? So how do these things resolve to be the same? So it will follow it first. The only real trick to it is there is a special named I node for the root directory. So if you do a path like this, it knows what the root I node is and spoiler alert, it's I node two, I think. I'm pretty sure it's I node two. So it knows to go to I node two. And then within I node two, it will look for the name called home inside that directory, because it will be a directory. Yeah, like the root, root I node is a directory I node. So within that, there'll be a bunch of names to other I nodes. So there would be in the root directory one, there would be a entry called home and they would point to an I node and that I node would also be a directory. So I would go in that directory and within that directory, it would be an entry called John, which would point to an I node that is again another directory. And then within that directory, you can see where this is going. There's something called examples, I'd follow it so you just have to go all the way through. And then for relatives pass, well, that's why there's a dot here. So since there's a dot, I mean, you can just get the I node for the current directory and you know it's a directory I node so you can figure it out. Yeah, technically it'd be faster to do relative pass because you don't have to start root unless you go all the way back and then all the way forward. Okay, so that, oh yeah, and then we can do a fun thing called RM. So RM, we'll see that doesn't actually delete anything. So we have two things point to the same I node. If I remove b.txt, well, didn't delete anything because we know b.txt and d.txt are the same content in the same actual file. It's still there, it's not deleted because there's still one reference to that I node. So if we start it again, we see that the number of links has decreased. It was two because two things point to it and now one thing points to it. So that I node will only be reclaimed and reused again if zero things point to it and we'll actually get deleted. So RM doesn't actually remove anything. All it actually removes is that name in the directory. So it just removes that entry for the name in the directory. That's it. If it's the last reference to the I node, it might get deleted but that's up to the kernel and it probably won't. Okay, so quickly because we have TA evaluations we need to fill in as well. So after all of this, it looks like this. C.txt points to the name to do.txt which doesn't actually exist so I'll put in a black background and then d.txt points to an I node that actually represents the original to do.txt but to do.txt has long been removed. So Linux, everything's a file. So directories are also I nodes. So we kind of saw that. So the only difference is that their file type is a directory and then there is a special format that says, it has to contain name to I node and the names again maximum size is 255 bytes. So you can create a path that's huge but each individual name is only 255 bytes. So other things they can be, there's regular files, there's block devices. So even your hard drives will be represented by a file and a block device just means that you can't access them byte by byte. You have to access them in big blocks. Yep, no, so that's, I know it represents a file. Yeah, so it represents a block device but it's just its representation. There's other ways to represent block device so I can access the whole thing. Yeah, so directory I nodes don't do anything that special. All they contain is name to I node. That's it. So we'll go through this quick. What's stored in I node? So the file name is not stored in an I node. The names only exist in a directory. That's the only place names exist. And then I nodes also do not know what containing directory they're in. They have no idea whatsoever. You have to follow all the links to figure out where it is. There's no back mapping or anything like that. They do contain the file size, so it's whatever it represents. They contain the file type. So regular files, symbolic link or directory are the main ones you'll probably encounter. If an I node is a soft link or just an I node doesn't even know how many soft links are pointing to it. Doesn't know where the location is. It however does know the number of hard links to it. So that was one of the things that are stored on it. So the kernel knows if it can actually delete what it points to. And then the location of hard links it doesn't know. And then other things that stores the access time stamps and file content sometimes. So that's that got you thing. So if it is a small symbolic link, the I node will actually contain the contents of that. Yeah. No, so a directory name doesn't contain any other, doesn't contain its own name. No. Yes. Yeah, which would be the contents of that I node, but not the I node itself. I see, okay. Yeah. Yeah, and then by definition, an I node will store an ordered list of data blocks. So one thing too is we saw using caches to speed up writes. So writes are slow, we can use a cache. So you could also cache a file system. So there'd be a file system cache. And sometimes you might want to bring in stuff ahead of time. That's like the prefetching thing that windows might do. So if you're referencing a block, you might wanna reference it again if it represents a database. So I'll keep it in memory instead of writing it back and forth to disk. And then if you're, sometimes you'll read a file sequentially. So maybe I just read it into memory ahead of time before you do it. So it's already there by the time you get it. And then the kernel is responsible for actually writing the changes back to the disk. And we saw that before with the write through stuff. And then the way to control that are there a system calls for flush and sync. And that will trigger the kernel to actually write data. Clear all the caches and actually write it to disk. So that's what they do. All right. Last thing quick is the journaling file system. So deleting a file has, it's like a three step process. So to actually delete the contents of a file, it would have to remove its directory entry. And then assuming that that's the last link to the inode, it would have to release the inode to the pool of free inodes. And then also record that all those disk blocks that that inode points to are now free. And they would be a bitmap. So they would have to zero them out. So if you care about data integrity, your power could go out at any point in this process. So my power goes out between one and two. Well, I'm not going to have any way to access the directory inode through names anymore, but it's going to look like it is still in use. And all the disk blocks it's using are going to look like they're in use. And then if I crash between step two and three, well, that inode's not even gonna exist anymore, but all the blocks it was pointing to are gonna be used and I can never reuse them again. Yeah. So in the directory type, the contents of that inode, so the blocks it points to, the data that it points to are going to just be name inode pairs. Always name inode. So inodes, a soft link is an inode. Is an inode soft link. Nope. So quick. So the directory does contain the soft link, but here if we look, so this is a soft link, right? But it's, whoops. That is not, it crashed, cool. Yeah. So it is an inode. So the soft link is itself an inode and the only way we see it to do .txt is because LS actually grabs the content of it. So if we look at it, itself is an inode and its type is symbolic link. So directory doesn't change name to inode. Okay. Yeah, they shouldn't. They shouldn't. Yeah. All right. Yeah. So last thing, journal. Basically it just writes what things are going to happen. So if it crashes, so it would write what it's about to do. And then if it crashes anywhere in step one, two or three, that entry would still be in the journal. So it knows where it needs to go look for to actually recover all that data and go through. And it can figure out where it crashed from there and then make everything consistent. And then the usual case for a journal is once it's done all the steps, it would go ahead and remove itself from the journal and then you know it's all consistent. So that's it. I guess there's office hours now and if you can, there's a TA thing. So just remember, going for it, we're on.