Вход на хостинг
IT-новости
20.04.2016 iPhone 2017 года поместят в водонепроницаемый корпус из стекла
Линейка iPhone в новом году серьезно поменяется. В этом уверен аналитический исследователь Мин Чи Ку......
30.07.2015 Ищем уникальный контент для сайта
Ищем уникальный контент для сайта Без уникального контента Ваш сайт обречен на то, что его страницы......
printf("Unit not ready ");
return -1;
}
return 0;
}
Чтение PMA выполняет функция read_pma():
int read_pma()
{
int i, k;
__u8 read_pma_cmd[10];
__u8 *pma_data_buff; // здесь будут сохранены результаты чтения PMA
__u16 buff_size = 0xFFFF; // размер блока памяти для хранения считываемых данных
__u16 pma_data_length = 0; // реальная длина записей PMA
__u32 lba;
int pma_entries = 0; // число записей PMA
pma_t *pma;
/* Проверяем готовность устройства к приему команды */
if(test_unit_ready() < 0) exit(-1);
pma_data_buff = (__u8 *)malloc(buff_size);
memset(pma_data_buff, 0, buff_size);
/* Формируем командный пакет */
memset(read_pma_cmd, 0, 10);
read_pma_cmd[0] = 0x43; // код команды READ_TOC/PMA/ATIP
read_pma_cmd[2] = 3; // поле Format Field = 011b, читаем PMA
read_pma_cmd[7] = 0xFF;
read_pma_cmd[8] = 0xFF;
/* Посылаем устройству команду */
if(send_cmd(read_pma_cmd, 10, SG_DXFER_FROM_DEV, pma_data_buff, buff_size, 20000) < 0) return -1;
/* Считываем длину записей PMA. Размер поля PMA Data Length (2 байта) не учитывается */
memcpy(&pma_data_length, pma_data_buff, 2);
pma_data_length = __swab16(pma_data_length);
printf("PMA data length - %d ", pma_data_length);
/* Определяем число записей PMA */
pma_entries = (pma_data_length - 2)/11;
printf("PMA entries - %d ", pma_entries);
/* Размер данных PMA точно известен и равен pma_data_length. Выделяем блок памяти для данных PMA и копируем их туда
* из pma_data_buff. После этого можно освободить блок памяти, на который указывает pma_data_buff
*/
pma = (pma_t *)malloc(pma_data_length);
memset((void *)pma, 0, pma_data_length);
memcpy((void *)pma, pma_data_buff + 4, pma_data_length);
free(pma_data_buff);
/* Отображаем данные PMA */
printf("Entry ADR CTRL Point Zero Min Sec Frame PMin Psec PFrame LBA ");
for(i = 0; i < pma_entries; i++) {
printf("%d ", i);
printf("%X ", (pma + i)->adr);
printf("%X ", (pma + i)->ctrl);
printf("%X ", (pma + i)->point);
printf("%d ", (pma + i)->zero);
printf("%d ", (pma + i)->min);
printf("%d ", (pma + i)->sec);
printf("%d ", (pma + i)->frame);
printf("%d ", (pma + i)->pmin);
printf("%d ", (pma + i)->psec);
printf("%d ", (pma + i)->pframe);
lba = MSF2LBA((pma + i)->pmin, (pma + i)->psec, (pma + i)->pframe);
if((pma + i)->adr != 1) printf("--- ");
else printf("%u ", lba);
}
free(pma);
return 0;
}
Вызов функции read_pma() для чтения данных PMA выполняется из главной функции:
Открываем файл устройства. Обратите внимание на режим открытия – чтение/запись. Если устройство открыто в режиме «Только чтение» (O_RDONLY), то оно воспринимает команды (см. [4]):