Esempio n. 1
0
/**
 * Parse mbr for filesystem
 */
void mount_all_devices() {
	FindPartitions(DEVICE_USB);
	if (xenon_ata_ops.isInserted()) {
		XTAFMount();
		FindPartitions(DEVICE_ATA);
	}
	if (xenon_atapi_ops.isInserted()) {
		FindPartitions(DEVICE_ATAPI);
	}
}
Esempio n. 2
0
void Close_USB()
{
	fatUnmount("usb");
	
	if (isUSB2)
	{
		__io_usbstorage2.shutdown();
	} else {
		__io_usbstorage.shutdown();
	}
}
Esempio n. 3
0
s32 Fat_UnmountSDHC(void)
{
	s32 ret;

	/* Unmount device */
	fatUnmount(SDHC_MOUNT);

	/* Shutdown SDHC interface */
	ret = __io_sdhc.shutdown();
	if (!ret)
		return -1;

	return 0;
}
Esempio n. 4
0
void Init_USB()
{
	//Close_USB();
	
	printf("\n");
	if (AHBPROT_DISABLED && !USB_PORT_CONNECTED)
	{
		USBmnt = false;
	} else {
		bool started = false;
		isUSB2 = (IOS_GetVersion() >= 200);
		
		time_t tStart = time(0);
		while ((time(0) - tStart) < 10) // 10 seconds timeout
		{
			Con_ClearLine();
			printf("\t- USB drive: %.f...", difftime(time(0), tStart));
			
			if (isUSB2)
			{
				started = (__io_usbstorage2.startup() && __io_usbstorage2.isInserted());
			} else {
				started = (__io_usbstorage.startup() && __io_usbstorage.isInserted());
			}
			
			if (started) break;
			
			usleep(50000);
		}
		
		USBmnt = (started && fatMountSimple("usb", (isUSB2 ? &__io_usbstorage2 : &__io_usbstorage)));
		Con_ClearLine();
	}
	
	printf("\t- USB drive: %s.\n\n", (USBmnt ? "OK" : "FAILED"));
}
Esempio n. 5
0
s32 Init_USB()
{
	if (!__io_usbstorage.startup())
	{
		printf("USB storage error, press any button to exit...\n");
		return -1;		
	}
	
	if (!fatMountSimple("usb", &__io_usbstorage))
	{
		printf("FAT error, press any button to exit...\n");
		return -1;
	}
	return 0;
}
Esempio n. 6
0
s32 Fat_MountSDHC(void)
{
	s32 ret;

	/* Initialize SDHC interface */
	ret = __io_sdhc.startup();
	if (!ret)
		return -1;

	/* Mount device */
	ret = fatMountSimple(SDHC_MOUNT, &__io_sdhc);
	if (!ret)
		return -2;

	return 0;
}
Esempio n. 7
0
static int FindPartitions(int device) {
	int i;
	int devnum = 0;

	// clear list
	for (i = 0; i < MAX_DEVICES; i++) {
		part[device][i].name[0] = 0;
		part[device][i].mount[0] = 0;
		part[device][i].sector = 0;
		part[device][i].interface = NULL;
		part[device][i].type = 0;
	}

	DISC_INTERFACE *interface;

	switch(device){
		case DEVICE_ATAPI:
			interface = (DISC_INTERFACE *) & xenon_atapi_ops;
			break;
		case DEVICE_ATA:
			interface = (DISC_INTERFACE *) & xenon_ata_ops;
			break;
		case DEVICE_USB:
			interface = (DISC_INTERFACE *) & usb2mass_ops;
			break;
	}


	MASTER_BOOT_RECORD mbr;
	PARTITION_RECORD *partition = NULL;
	devnum = 0;
	sec_t part_lba = 0;

	union {
		u8 buffer[BYTES_PER_SECTOR];
		MASTER_BOOT_RECORD mbr;
		EXTENDED_BOOT_RECORD ebr;
		NTFS_BOOT_SECTOR boot;
	} sector;

	if(device == DEVICE_ATAPI){
		AddPartition(0, device, T_ISO9660, &devnum);
		return devnum;
	}

	// Read the first sector on the device
	if (!interface->readSectors(0, 1, &sector.buffer)) {
		//errno = EIO;
		return -1;
	}

	// If this is the devices master boot record
	debug_printf("0x%x\n", sector.mbr.signature);
	if (sector.mbr.signature == MBR_SIGNATURE) {
		memcpy(&mbr, &sector, sizeof (MASTER_BOOT_RECORD));
		debug_printf("Valid Master Boot Record found\n");

		// Search the partition table for all partitions (max. 4 primary partitions)
		for (i = 0; i < 4; i++) {
			partition = &mbr.partitions[i];
			part_lba = le32_to_cpu(mbr.partitions[i].lba_start);

			debug_printf(
					"Partition %i: %s, sector %u, type 0x%x\n",
					i + 1,
					partition->status == PARTITION_STATUS_BOOTABLE ? "bootable (active)"
					: "non-bootable", part_lba, partition->type);

			// Figure out what type of partition this is
			switch (partition->type) {
					// NTFS partition
				case PARTITION_TYPE_NTFS:
				{
					debug_printf("Partition %i: Claims to be NTFS\n", i + 1);

					// Read and validate the NTFS partition
					if (interface->readSectors(part_lba, 1, &sector)) {
						debug_printf("sector.boot.oem_id: 0x%x\n", sector.boot.oem_id);
						debug_printf("NTFS_OEM_ID: 0x%x\n", NTFS_OEM_ID);
						if (sector.boot.oem_id == NTFS_OEM_ID) {
							debug_printf("Partition %i: Valid NTFS boot sector found\n", i + 1);
							AddPartition(part_lba, device, T_NTFS, &devnum);
						} else {
							debug_printf("Partition %i: Invalid NTFS boot sector, not actually NTFS\n", i + 1);
						}
					}
					break;
				}
					// DOS 3.3+ or Windows 95 extended partition
				case PARTITION_TYPE_DOS33_EXTENDED:
				case PARTITION_TYPE_WIN95_EXTENDED:
				{
					debug_printf("Partition %i: Claims to be Extended\n", i + 1);

					// Walk the extended partition chain, finding all NTFS partitions within it
					sec_t ebr_lba = part_lba;
					sec_t next_erb_lba = 0;
					do {
						// Read and validate the extended boot record
						if (interface->readSectors(ebr_lba + next_erb_lba, 1, &sector)) {
							if (sector.ebr.signature == EBR_SIGNATURE) {
								debug_printf(
										"Logical Partition @ %d: %s type 0x%x\n",
										ebr_lba + next_erb_lba,
										sector.ebr.partition.status
										== PARTITION_STATUS_BOOTABLE ? "bootable (active)"
										: "non-bootable",
										sector.ebr.partition.type);

								// Get the start sector of the current partition
								// and the next extended boot record in the chain
								part_lba = ebr_lba + next_erb_lba
										+ le32_to_cpu(
										sector.ebr.partition.lba_start);
								next_erb_lba = le32_to_cpu(
										sector.ebr.next_ebr.lba_start);

								if (sector.ebr.partition.type == PARTITION_TYPE_LINUX) {
									debug_printf("Partition : type ext2/3/4 found\n");
									AddPartition(part_lba, device, T_EXT2, &devnum);
								}// Check if this partition has a valid NTFS boot record
								else if (interface->readSectors(part_lba, 1, &sector)) {
									if (sector.boot.oem_id == NTFS_OEM_ID) {
										debug_printf(
												"Logical Partition @ %d: Valid NTFS boot sector found\n",
												part_lba);
										if (sector.ebr.partition.type
												!= PARTITION_TYPE_NTFS) {
											debug_printf(
													"Logical Partition @ %d: Is NTFS but type is 0x%x; 0x%x was expected\n",
													part_lba,
													sector.ebr.partition.type,
													PARTITION_TYPE_NTFS);
										}
										AddPartition(part_lba, device, T_NTFS, &devnum);
									} else if (!memcmp(sector.buffer
											+ BPB_FAT16_fileSysType, FAT_SIG,
											sizeof (FAT_SIG)) || !memcmp(
											sector.buffer
											+ BPB_FAT32_fileSysType,
											FAT_SIG, sizeof (FAT_SIG))) {
										debug_printf("Partition : Valid FAT boot sector found\n");
										AddPartition(part_lba, device, T_FAT, &devnum);
									}
								}
							} else {
								next_erb_lba = 0;
							}
						}
					} while (next_erb_lba);
					break;
				}
				case PARTITION_TYPE_LINUX:
				{
					debug_printf("Partition %i: Claims to be LINUX\n", i + 1);

					// Read and validate the EXT2 partition
					AddPartition(part_lba, device, T_EXT2, &devnum);
					break;
				}
					// Ignore empty partitions
				case PARTITION_TYPE_EMPTY:
					debug_printf("Partition %i: Claims to be empty\n", i + 1);
					// Unknown or unsupported partition type
				default:
				{
					// Check if this partition has a valid NTFS boot record anyway,
					// it might be misrepresented due to a lazy partition editor
					if (interface->readSectors(part_lba, 1, &sector)) {
						if (sector.boot.oem_id == NTFS_OEM_ID) {
							debug_printf("Partition %i: Valid NTFS boot sector found\n", i + 1);
							if (partition->type != PARTITION_TYPE_NTFS) {
								debug_printf(
										"Partition %i: Is NTFS but type is 0x%x; 0x%x was expected\n",
										i + 1, partition->type,
										PARTITION_TYPE_NTFS);
							}
							AddPartition(part_lba, device, T_NTFS, &devnum);
						} else if (!memcmp(sector.buffer + BPB_FAT16_fileSysType,
								FAT_SIG, sizeof (FAT_SIG)) || !memcmp(
								sector.buffer + BPB_FAT32_fileSysType, FAT_SIG,
								sizeof (FAT_SIG))) {
							debug_printf("Partition : Valid FAT boot sector found\n");
							AddPartition(part_lba, device, T_FAT, &devnum);
						} else {
							debug_printf("Trying : ext partition\n");
							AddPartition(part_lba, device, T_EXT2, &devnum);
						}
					}
					break;
				}
			}
		}
	}
	if (devnum == 0) // it is assumed this device has no master boot record or no partitions found
	{
		debug_printf("No Master Boot Record was found or no partitions found!\n");

		// As a last-ditched effort, search the first 64 sectors of the device for stray NTFS/FAT partitions
		for (i = 0; i < 64; i++) {
			if (interface->readSectors(i, 1, &sector)) {
				if (sector.boot.oem_id == NTFS_OEM_ID) {
					debug_printf("Valid NTFS boot sector found at sector %d!\n", i);
					AddPartition(i, device, T_NTFS, &devnum);
					break;
				} else if (!memcmp(sector.buffer + BPB_FAT16_fileSysType, FAT_SIG,
						sizeof (FAT_SIG)) || !memcmp(sector.buffer
						+ BPB_FAT32_fileSysType, FAT_SIG, sizeof (FAT_SIG))) {
					debug_printf("Partition : Valid FAT boot sector found\n");
					AddPartition(i, device, T_FAT, &devnum);
					break;
				} else {
					debug_printf("Trying : ext partition\n");
					AddPartition(part_lba, device, T_EXT2, &devnum);
				}
			}
		}
	}
	return devnum;
}
Esempio n. 8
0
int main(void)
{
int fd,n,mounted=0;
int inited=0;
ipcmessage* message;


	memset(&my_reent, 0, sizeof(struct _reent));
	memset(my_filestr, 0, sizeof(FILE_STRUCT)*5);
	memset(file_table, 0, 4*2*5);

	memset(&dir_state_internal,0,sizeof(DIR_STATE_STRUCT));

	dir_internal.device=0;
	dir_internal.dirStruct=&dir_state_internal;

	

	heaphandle = os_heap_create(heapspace, sizeof(heapspace));

	void* queuespace = os_heap_alloc(heaphandle, 0x20);

	queuehandle = os_message_queue_create(queuespace, 8);

	 void* timer1_queuespace = os_heap_alloc(heaphandle, 0x40);

	timer1_queuehandle = os_message_queue_create(timer1_queuespace, 16);
	timer1_id=os_create_timer(1000*1000, 1, timer1_queuehandle, 0x666);
	os_stop_timer(timer1_id);

	 
	extern DISC_INTERFACE __io_wiisd;
	inited=__io_wiisd.startup();
	msleep(100);

	os_device_register(DEVICE, queuehandle);
	while(1)
		{
		int result = 1;
		int ack = 1;

		os_message_queue_receive(queuehandle,(void *) &message, 0);
		
		switch( message->command )
		{
		
	    case IOS_OPEN:
			{
			result = -6;

                                //debug_printf("%s try open %sfor fd %d\n",DEVICE,message->open.device,message->open.resultfd);
				// Checking device name
				if (0 == strcmp(message->open.device, DEVICE))
                                  {
									result = message->open.resultfd;        
                                  }
				else
				if (0 == strcmp(message->open.device, DEVICE"/log"))
                                  {
								  if(inited && !mounted) 
										mounted=fatMountSimple("sd", &__io_wiisd);

								  if(mounted)
									{
									static char log_name[]="sd:/log000.txt";
									for(n=0;n<5;n++) if(my_filestr[n].inUse==0) break;
									fd=-1;
									if(n!=5)
										{
										my_reent._errno=0;
										fd=_FAT_open_r(&my_reent, &my_filestr[n], log_name, O_CREAT | O_TRUNC | O_RDWR, 0);
										log_name[9]++;
										if(log_name[9]>='9') {log_name[9]='0';log_name[8]++;}
										if(log_name[8]>='9') {log_name[8]='0';log_name[7]++;}
										if(log_name[7]>='9') {log_name[7]='0';log_name[8]='0';log_name[9]='0';}

										}
									
									if(fd<0) result=-1; 
									else 
										{
										result=file_table[n][0]=message->open.resultfd;
										file_table[n][1]= fd;
										}
									}
                        
                                  }
				else if (0 == memcmp(message->open.device, DEVICE"/", sizeof(DEVICE)))
                                        
				{
				if(inited && !mounted) 
					mounted=fatMountSimple("sd", &__io_wiisd);

				if(mounted)
					{
					for(n=0;n<5;n++) if(my_filestr[n].inUse==0) break;
					fd=-1;
					if(n!=5)
						{
						my_reent._errno=0;
						fd=_FAT_open_r(&my_reent, &my_filestr[n], message->open.device+sizeof(DEVICE),
							message->open.mode, 0);	
							
						}

					if(fd<0) result=-1; 
					else 
						{
						result=file_table[n][0]=message->open.resultfd;
						file_table[n][1]= fd;
						}
					}
				}
			
					
			}	
			break;

		case IOS_IOCTLV:
			{
			result = -1;

			ioctlv *vec = message->ioctlv.vector;

                                int i,in = message->ioctlv.num_in,io= message->ioctlv.num_io;
                               
                                os_sync_before_read( vec, (in+io)*sizeof(ioctlv));

                                for(i=0;i<in+io;i++){
                                        os_sync_before_read( vec[i].data, vec[i].len);
                                      
                                }

			#if 0
			// list the directory content to directory.txt
			switch(message->ioctl.command )
				{
				
				case 0xcacafea:
				if(inited && !mounted) 
						mounted=fatMountSimple("sd", &__io_wiisd);

				if(mounted)
					{
					my_reent._errno=0;
					
					result=-666;
					if(_FAT_diropen_r(&my_reent, &dir_internal, "sd:/"))
						{
						static char log_name2[]="sd:/directory.txt";
						char filename[768];

						result = 0;
						my_reent._errno=0;
						fd=_FAT_open_r(&my_reent, &my_filestr[4], log_name2, O_CREAT | O_TRUNC | O_RDWR, 0);
						my_reent._errno=0;
						while(!_FAT_dirnext_r (&my_reent, &dir_internal, filename, &filestat))
							{
							my_reent._errno=0;
							
							if(fd>=0)
								{
								if(filestat.st_mode & S_IFDIR)_FAT_write_r (&my_reent, fd, "[", 1); // es directorio
								_FAT_write_r (&my_reent, fd, filename, strlen(filename));
								if(filestat.st_mode & S_IFDIR)_FAT_write_r (&my_reent, fd, "]", 1); // es directorio
								_FAT_write_r (&my_reent, fd, "\n", 1);
								
								}
							
							}
							my_reent._errno=0;
							if(fd>=0) _FAT_close_r (&my_reent, fd);fd=-1;

						  _FAT_dirclose_r(&my_reent, &dir_internal);
						}

					
					}
				break;
				}
			#endif
				for(i=in;i<in+io;i++){
											os_sync_after_write( vec[i].data, vec[i].len);
									}
			
			}
			break;

		case IOS_CLOSE:
			{
			result = -1;
			if(mounted)
				{
				my_reent._errno=0;
				for(n=0;n<5;n++)
					{
					if(message->fd==file_table[n][0])
						{
						fd=file_table[n][1];
						file_table[n][0]=file_table[n][1]=0;
						_FAT_close_r (&my_reent, fd);
						result = 0;
						break;
						}
					}

				for(n=0;n<5;n++) if(my_filestr[n].inUse!=0) break;
					  
				if(n==5) {fatUnmount ("sd");mounted=0;}
				
				}
				else result=-6;
				
			}	
			break;

		case IOS_READ:
			{
			
			result=-1;
			if(mounted)
				{
				my_reent._errno=0;
				for(n=0;n<5;n++)
					{
					if(message->fd==file_table[n][0])
						{
						fd=file_table[n][1];
						result=_FAT_read_r (&my_reent, fd, message->write.data, message->write.length);
						}
					}
				}
			os_sync_after_write( message->write.data, message->write.length);
			}	
			break;

		case IOS_WRITE:
			{
		
			os_sync_before_read( message->write.data, message->write.length);

			result=-1;
			if(mounted)
				{
				my_reent._errno=0;
				for(n=0;n<5;n++)
					{
					if(message->fd==file_table[n][0])
						{
						fd=file_table[n][1];
						result=_FAT_write_r (&my_reent, fd, message->write.data, message->write.length);
						}
					}
				}		
			}	
			break;

		case IOS_SEEK:
			{
			result=-1;
			if(mounted)
				{
				my_reent._errno=0;
				for(n=0;n<5;n++)
					{
					if(message->fd==file_table[n][0])
						{
						fd=file_table[n][1];
						result=_FAT_seek_r (&my_reent, fd, message->seek.offset, message->seek.origin);
						}
					}
				}		
			}
			break;

		default:
			result=-1;
			break;

		}

		if (ack)
			os_message_queue_ack( (void*)message, result );

		}

	return 0;
}
Esempio n. 9
0
int main(int argc, char **argv)
{
	// Exit after 10 seconds if there is an error
	__exception_setreload(10);
//	u64 timeout = 0;
	CheckForGecko();
	DCInvalidateRange(loader_stub, 0x1800);
	memcpy(loader_stub, (void*)0x80001800, 0x1800);

	RAMInit();

	//Meh, doesnt do anything anymore anyways
	//STM_RegisterEventHandler(HandleSTMEvent);

	Initialise();

	// Checking for storage devices...
	ShowMessageScreen("Checking storage devices...");

	u32 u;
	//Disables MEMPROT for patches
	write16(MEM_PROT, 0);
	//Patches FS access
	for( u = 0x93A00000; u < 0x94000000; u+=2 )
	{
		if( memcmp( (void*)(u), FSAccessPattern, sizeof(FSAccessPattern) ) == 0 )
		{
		//	gprintf("FSAccessPatch:%08X\r\n", u );
			memcpy( (void*)u, FSAccessPatch, sizeof(FSAccessPatch) );
			DCFlushRange((void*)u, sizeof(FSAccessPatch));
			break;
		}
	}

	//for BT.c
	CONF_GetPadDevices((conf_pads*)0x932C0000);
	DCFlushRange((void*)0x932C0000, sizeof(conf_pads));
	*(vu32*)0x932C0490 = CONF_GetIRSensitivity();
	*(vu32*)0x932C0494 = CONF_GetSensorBarPosition();
	DCFlushRange((void*)0x932C0490, 8);

	if(LoadKernel() < 0)
	{
		ClearScreen();
		gprintf("Failed to load kernel from NAND!\r\n");
		ShowMessageScreenAndExit("Failed to load kernel from NAND!", 1);
	}
	InsertModule((char*)kernel_bin, kernel_bin_size);

	memset( (void*)0x92f00000, 0, 0x100000 );
	DCFlushRange( (void*)0x92f00000, 0x100000 );

	DCInvalidateRange( (void*)0x939F02F0, 0x20 );

	memcpy( (void*)0x939F02F0, Boot2Patch, sizeof(Boot2Patch) );

	DCFlushRange( (void*)0x939F02F0, 0x20 );

	//libogc still has that, lets close it
	__ES_Close();
	s32 fd = IOS_Open( "/dev/es", 0 );

	memset( STATUS, 0xFFFFFFFF, 0x20  );
	DCFlushRange( STATUS, 0x20 );

	memset( (void*)0x91000000, 0xFFFFFFFF, 0x20  );
	DCFlushRange( (void*)0x91000000, 0x20 );

	*(vu32*)0xD3003420 = 0; //make sure kernel doesnt reload

	raw_irq_handler_t irq_handler = BeforeIOSReload();
	IOS_IoctlvAsync( fd, 0x1F, 0, 0, &IOCTL_Buf, NULL, NULL );
	AfterIOSReload( irq_handler, FoundVersion );

	while(1)
	{
		DCInvalidateRange( STATUS, 0x20 );
		if((STATUS_LOADING > 0 || abs(STATUS_LOADING) > 1) && STATUS_LOADING < 20)
		{
			gprintf("Kernel sent signal\n");
			break;
		}
	}

	/* For slow USB HDDs */
	time_t timeout = time(NULL);
	while(time(NULL) - timeout < 10)
	{
		if(__io_custom_usbstorage.startup() && __io_custom_usbstorage.isInserted())
			break;
		usleep(50000);
	}
	fatInitDefault();

	gprintf("Nintendont at your service!\r\n%s\r\n", NIN_BUILD_STRING);
	KernelLoaded = 1;

	char* first_slash = strrchr(argv[0], '/');
	if (first_slash != NULL) strncpy(launch_dir, argv[0], first_slash-argv[0]+1);
	gprintf("launch_dir = %s\r\n", launch_dir);

	FPAD_Init();
	FPAD_Update();

	/* Read IPL Font before doing any patches */
	void *fontbuffer = memalign(32, 0x50000);
	__SYS_ReadROM((void*)fontbuffer,0x50000,0x1AFF00);
	memcpy((void*)0xD3100000, fontbuffer, 0x50000);
	DCInvalidateRange( (void*)0x93100000, 0x50000 );
	free(fontbuffer);
	//gprintf("Font: 0x1AFF00 starts with %.4s, 0x1FCF00 with %.4s\n", (char*)0x93100000, (char*)0x93100000 + 0x4D000);

	// Simple code to autoupdate the meta.xml in Nintendont's folder
	FILE *meta = fopen("meta.xml", "w");
	if(meta != NULL)
	{
		fprintf(meta, "%s\r\n<app version=\"1\">\r\n\t<name>%s</name>\r\n", META_XML, META_NAME);
		fprintf(meta, "\t<coder>%s</coder>\r\n\t<version>%d.%d</version>\r\n", META_AUTHOR, NIN_VERSION>>16, NIN_VERSION&0xFFFF);
		fprintf(meta, "\t<release_date>20150531000000</release_date>\r\n");
		fprintf(meta, "\t<short_description>%s</short_description>\r\n", META_SHORT);
		fprintf(meta, "\t<long_description>%s\r\n\r\n%s</long_description>\r\n", META_LONG1, META_LONG2);
		fprintf(meta, "\t<ahb_access/>\r\n</app>");
		fclose(meta);
	}
Esempio n. 10
0
int isInserted(const char *path) {
    if (!strncmp(path, "USB:", 4))
        return 1;

    return __io_sdhc.isInserted() || __io_wiisd.isInserted();
}