// File: /workspace/github_c_makefile_star2_O0/gadget114514[P]fatfs-example/fatfs/source/ff.c
// Function: follow_path
static
FRESULT follow_path (	/* FR_OK(0): successful, !=0: error code */
	DIR* dp,			/* Directory object to return last directory and found object */
	const TCHAR* path	/* Full-path string to find a file or directory */
)
{
	FRESULT res;
	BYTE ns;
	FATFS *fs = dp->obj.fs;


#if FF_FS_RPATH != 0
	if (*path != '/' && *path != '\\') {	/* Without heading separator */
		dp->obj.sclust = fs->cdir;				/* Start from current directory */
	} else
#endif
	{										/* With heading separator */
		while (*path == '/' || *path == '\\') path++;	/* Strip heading separator */
		dp->obj.sclust = 0;					/* Start from root directory */
	}
#if FF_FS_EXFAT
	dp->obj.n_frag = 0;	/* Invalidate last fragment counter of the object */
#if FF_FS_RPATH != 0
	if (fs->fs_type == FS_EXFAT && dp->obj.sclust) {	/* exFAT: Retrieve the sub-directory's status */
		DIR dj;

		dp->obj.c_scl = fs->cdc_scl;
		dp->obj.c_size = fs->cdc_size;
		dp->obj.c_ofs = fs->cdc_ofs;
		res = load_obj_xdir(&dj, &dp->obj);
		if (res != FR_OK) return res;
		dp->obj.objsize = ld_dword(fs->dirbuf + XDIR_FileSize);
		dp->obj.stat = fs->dirbuf[XDIR_GenFlags] & 2;
	}
#endif
#endif

	if ((UINT)*path < ' ') {				/* Null path name is the origin directory itself */
		dp->fn[NSFLAG] = NS_NONAME;
		res = dir_sdi(dp, 0);

	} else {								/* Follow path */
		for (;;) {
			res = create_name(dp, &path);	/* Get a segment name of the path */
			if (res != FR_OK) break;
			res = dir_find(dp);				/* Find an object with the segment name */
			ns = dp->fn[NSFLAG];
			if (res != FR_OK) {				/* Failed to find the object */
				if (res == FR_NO_FILE) {	/* Object is not found */
					if (FF_FS_RPATH && (ns & NS_DOT)) {	/* If dot entry is not exist, stay there */
						if (!(ns & NS_LAST)) continue;	/* Continue to follow if not last segment */
						dp->fn[NSFLAG] = NS_NONAME;
						res = FR_OK;
					} else {							/* Could not find the object */
						if (!(ns & NS_LAST)) res = FR_NO_PATH;	/* Adjust error code if not last segment */
					}
				}
				break;
			}
			if (ns & NS_LAST) break;			/* Last segment matched. Function completed. */
			/* Get into the sub-directory */
			if (!(dp->obj.attr & AM_DIR)) {		/* It is not a sub-directory and cannot follow */
				res = FR_NO_PATH; break;
			}
#if FF_FS_EXFAT
			if (fs->fs_type == FS_EXFAT) {		/* Save containing directory information for next dir */
				dp->obj.c_scl = dp->obj.sclust;
				dp->obj.c_size = ((DWORD)dp->obj.objsize & 0xFFFFFF00) | dp->obj.stat;
				dp->obj.c_ofs = dp->blk_ofs;
				init_alloc_info(fs, &dp->obj);	/* Open next directory */
			} else
#endif
			{
				dp->obj.sclust = ld_clust(fs, fs->win + dp->dptr % SS(fs));	/* Open next directory */
			}
		}
	}

	return res;
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
subq $0x30, %rsp
movq %rdi, -0x8(%rbp)
movq %rsi, -0x10(%rbp)
movq -0x8(%rbp), %rax
movq (%rax), %rax
movq %rax, -0x20(%rbp)
movq -0x10(%rbp), %rax
movsbl (%rax), %ecx
movb $0x1, %al
cmpl $0x2f, %ecx
movb %al, -0x21(%rbp)
je 0x247c
movq -0x10(%rbp), %rax
movsbl (%rax), %eax
cmpl $0x5c, %eax
sete %al
movb %al, -0x21(%rbp)
movb -0x21(%rbp), %al
testb $0x1, %al
jne 0x2485
jmp 0x2493
movq -0x10(%rbp), %rax
addq $0x1, %rax
movq %rax, -0x10(%rbp)
jmp 0x245b
movq -0x8(%rbp), %rax
movq $0x0, 0x10(%rax)
movq -0x10(%rbp), %rax
movsbl (%rax), %eax
cmpl $0x20, %eax
jae 0x24c8
movq -0x8(%rbp), %rax
movb $-0x80, 0x4b(%rax)
movq -0x8(%rbp), %rdi
xorl %eax, %eax
movl %eax, %esi
callq 0x4020
movl %eax, -0x14(%rbp)
jmp 0x2579
jmp 0x24ca
movq -0x8(%rbp), %rdi
leaq -0x10(%rbp), %rsi
callq 0x62f0
movl %eax, -0x14(%rbp)
cmpl $0x0, -0x14(%rbp)
je 0x24e5
jmp 0x2577
movq -0x8(%rbp), %rdi
callq 0x6530
movl %eax, -0x14(%rbp)
movq -0x8(%rbp), %rax
movb 0x4b(%rax), %al
movb %al, -0x15(%rbp)
cmpl $0x0, -0x14(%rbp)
je 0x251e
cmpl $0x4, -0x14(%rbp)
jne 0x251c
movzbl -0x15(%rbp), %eax
andl $0x4, %eax
cmpl $0x0, %eax
jne 0x251a
movl $0x5, -0x14(%rbp)
jmp 0x251c
jmp 0x2577
movzbl -0x15(%rbp), %eax
andl $0x4, %eax
cmpl $0x0, %eax
je 0x252c
jmp 0x2577
movq -0x8(%rbp), %rax
movzbl 0xa(%rax), %eax
andl $0x10, %eax
cmpl $0x0, %eax
jne 0x2545
movl $0x5, -0x14(%rbp)
jmp 0x2577
movq -0x20(%rbp), %rdi
movq -0x20(%rbp), %rsi
addq $0x58, %rsi
movq -0x8(%rbp), %rax
movq 0x20(%rax), %rax
andq $0x1ff, %rax            # imm = 0x1FF
addq %rax, %rsi
callq 0x2620
movq %rax, %rcx
movq -0x8(%rbp), %rax
movq %rcx, 0x10(%rax)
jmp 0x24ca
jmp 0x2579
movl -0x14(%rbp), %eax
addq $0x30, %rsp
popq %rbp
retq
nopw %cs:(%rax,%rax)