コード例 #1
0
ファイル: filetree.c プロジェクト: AMPed126/libmtp-zune
void recursive_file_tree(LIBMTP_mtpdevice_t *device,
			 LIBMTP_devicestorage_t *storage,
			 uint32_t leaf,
			 int depth)
{
  LIBMTP_file_t *files;
  LIBMTP_file_t *file;

  files = LIBMTP_Get_Files_And_Folders(device,
				      storage->id,
				      leaf);
  if (files == NULL) {
    return;
  }

  /* Iterate over the filelisting */
  for (file = files; file != NULL; file = file->next) {
    int i;

    /* Indent */
    for (i = 0; i < depth; i++) {
      printf(" ");
    }
    printf("%u %s\n", file->item_id, file->filename);
    if (file->filetype == LIBMTP_FILETYPE_FOLDER) {
      recursive_file_tree(device, storage, file->item_id, depth+2);
    }
  }
}
コード例 #2
0
ファイル: libmtp.c プロジェクト: AEliu/calibre
static int recursive_get_files(LIBMTP_mtpdevice_t *dev, uint32_t storage_id, uint32_t parent_id, PyObject *ans, PyObject *errs, PyObject *callback, unsigned int level) {
    LIBMTP_file_t *f, *files;
    PyObject *entry, *r;
    int ok = 1, recurse;

    Py_BEGIN_ALLOW_THREADS;
    files = LIBMTP_Get_Files_And_Folders(dev, storage_id, parent_id);
    Py_END_ALLOW_THREADS;

    if (files == NULL) return ok;

    for (f = files; ok && f != NULL; f = f->next) {
        entry = build_file_metadata(f, storage_id);
        if (entry == NULL) { ok = 0; }
        else {
            r = PyObject_CallFunction(callback, "OI", entry, level);
            recurse = (r != NULL && PyObject_IsTrue(r)) ? 1 : 0;
            Py_XDECREF(r);
            if (PyList_Append(ans, entry) != 0) { ok = 0; }
            Py_DECREF(entry); 
        }

        if (ok && recurse && f->filetype == LIBMTP_FILETYPE_FOLDER) {
            if (!recursive_get_files(dev, storage_id, f->item_id, ans, errs, callback, level+1)) {
                ok = 0; 
            }
        }
    }

    // Release memory
    f = files;
    while (f != NULL) {
        files = f; f = f->next; LIBMTP_destroy_file_t(files);
    }

    return ok;
}
コード例 #3
0
const TypeDir *MTPDevice::dirFetchContent(std::string path)
{
    if (!m_root_dir.isFetched()) {
        for (LIBMTP_devicestorage_t *s = m_device->storage; s; s = s->next) {
            m_root_dir.addDir(TypeDir(s_root_node, 0, s->id,
                std::string(s->StorageDescription)));
            m_root_dir.setFetched();
        }
    }

    if (m_root_dir.dirCount() == 1)
        path = '/' + m_root_dir.dirs().begin()->name() + path;

    if (path == "/")
        return &m_root_dir;

    std::string member;
    std::istringstream ss(path);
    TypeDir *dir = &m_root_dir;
    while (std::getline(ss, member, '/')) {
        if (member.empty())
            continue;

        const TypeDir *tmp = dir->dir(member);
        if (!tmp && !dir->isFetched()) {
            criticalEnter();
            LIBMTP_file_t *content = LIBMTP_Get_Files_And_Folders(
                m_device, dir->storageid(), dir->id());
            criticalLeave();
            for (LIBMTP_file_t *f = content; f; f = f->next) {
                if (f->filetype == LIBMTP_FILETYPE_FOLDER)
                    dir->addDir(TypeDir(f));
                else
                    dir->addFile(TypeFile(f));
            }
            LIBMTP_Free_Files_And_Folders(&content);
            dir->setFetched();
            tmp = dir->dir(member);
        }

        if (!tmp)
            return nullptr;
        dir = const_cast<TypeDir*>(tmp);
    }

    if (dir->isFetched())
        return dir;

    criticalEnter();
    dir->setFetched();
    LIBMTP_file_t *content = LIBMTP_Get_Files_And_Folders(
        m_device, dir->storageid(), dir->id());
    criticalLeave();
    for (LIBMTP_file_t *f = content; f; f = f->next) {
        if (f->filetype == LIBMTP_FILETYPE_FOLDER)
            dir->addDir(TypeDir(f));
        else
            dir->addFile(TypeFile(f));
    }
    LIBMTP_Free_Files_And_Folders(&content);
    return dir;
}
コード例 #4
0
ファイル: detect.c プロジェクト: reverendhomer/libmtp
int main (int argc, char **argv)
{
    LIBMTP_raw_device_t * rawdevices;
    int numrawdevices;
    LIBMTP_error_number_t err;
    int i;

    int opt;
    extern int optind;
    extern char *optarg;

    while ((opt = getopt(argc, argv, "d")) != -1 ) {
        switch (opt) {
        case 'd':
            LIBMTP_Set_Debug(LIBMTP_DEBUG_PTP | LIBMTP_DEBUG_DATA);
            break;
        }
    }

    argc -= optind;
    argv += optind;

    LIBMTP_Init();

    fprintf(stdout, "libmtp version: " LIBMTP_VERSION_STRING "\n\n");

    fprintf(stdout, "Listing raw device(s)\n");
    err = LIBMTP_Detect_Raw_Devices(&rawdevices, &numrawdevices);
    switch(err) {
    case LIBMTP_ERROR_NO_DEVICE_ATTACHED:
        fprintf(stdout, "   No raw devices found.\n");
        return 0;
    case LIBMTP_ERROR_CONNECTING:
        fprintf(stderr, "Detect: There has been an error connecting. Exiting\n");
        return 1;
    case LIBMTP_ERROR_MEMORY_ALLOCATION:
        fprintf(stderr, "Detect: Encountered a Memory Allocation Error. Exiting\n");
        return 1;
    case LIBMTP_ERROR_NONE:
    {
        int i;

        fprintf(stdout, "   Found %d device(s):\n", numrawdevices);
        for (i = 0; i < numrawdevices; i++) {
            if (rawdevices[i].device_entry.vendor != NULL ||
                    rawdevices[i].device_entry.product != NULL) {
                fprintf(stdout, "   %s: %s (%04x:%04x) @ bus %d, dev %d\n",
                        rawdevices[i].device_entry.vendor,
                        rawdevices[i].device_entry.product,
                        rawdevices[i].device_entry.vendor_id,
                        rawdevices[i].device_entry.product_id,
                        rawdevices[i].bus_location,
                        rawdevices[i].devnum);
            } else {
                fprintf(stdout, "   %04x:%04x @ bus %d, dev %d\n",
                        rawdevices[i].device_entry.vendor_id,
                        rawdevices[i].device_entry.product_id,
                        rawdevices[i].bus_location,
                        rawdevices[i].devnum);
            }
        }
    }
    break;
    case LIBMTP_ERROR_GENERAL:
    default:
        fprintf(stderr, "Unknown connection error.\n");
        return 1;
    }

    /* Iterate over connected MTP devices */
    fprintf(stdout, "Attempting to connect device(s)\n");
    for (i = 0; i < numrawdevices; i++) {
        LIBMTP_mtpdevice_t *device;
        LIBMTP_devicestorage_t *storage;
        char *friendlyname;
        char *syncpartner;
        char *sectime;
        char *devcert;
        uint16_t *filetypes;
        uint16_t filetypes_len;
        uint8_t maxbattlevel;
        uint8_t currbattlevel;
        int ret;

        device = LIBMTP_Open_Raw_Device_Uncached(&rawdevices[i]);
        if (device == NULL) {
            fprintf(stderr, "Unable to open raw device %d\n", i);
            continue;
        }

        LIBMTP_Dump_Errorstack(device);
        LIBMTP_Clear_Errorstack(device);
        LIBMTP_Dump_Device_Info(device);

        printf("MTP-specific device properties:\n");
        // The friendly name
        friendlyname = LIBMTP_Get_Friendlyname(device);
        if (friendlyname == NULL) {
            fprintf(stdout, "   Friendly name: (NULL)\n");
        } else {
            fprintf(stdout, "   Friendly name: %s\n", friendlyname);
            free(friendlyname);
        }
        syncpartner = LIBMTP_Get_Syncpartner(device);
        if (syncpartner == NULL) {
            fprintf(stdout, "   Synchronization partner: (NULL)\n");
        } else {
            fprintf(stdout, "   Synchronization partner: %s\n", syncpartner);
            free(syncpartner);
        }

        // Some battery info
        ret = LIBMTP_Get_Batterylevel(device, &maxbattlevel, &currbattlevel);
        if (ret == 0) {
            fprintf(stdout, "   Battery level %d of %d (%d%%)\n",currbattlevel, maxbattlevel,
                    (int) ((float) currbattlevel/ (float) maxbattlevel * 100.0));
        } else {
            // Silently ignore. Some devices does not support getting the
            // battery level.
            LIBMTP_Clear_Errorstack(device);
        }

        ret = LIBMTP_Get_Supported_Filetypes(device, &filetypes, &filetypes_len);
        if (ret == 0) {
            uint16_t i;

            printf("libmtp supported (playable) filetypes:\n");
            for (i = 0; i < filetypes_len; i++) {
                fprintf(stdout, "   %s\n", LIBMTP_Get_Filetype_Description(filetypes[i]));
            }
        } else {
            LIBMTP_Dump_Errorstack(device);
            LIBMTP_Clear_Errorstack(device);
        }

        // Secure time XML fragment
        ret = LIBMTP_Get_Secure_Time(device, &sectime);
        if (ret == 0 && sectime != NULL) {
            fprintf(stdout, "\nSecure Time:\n%s\n", sectime);
            free(sectime);
        } else {
            // Silently ignore - there may be devices not supporting secure time.
            LIBMTP_Clear_Errorstack(device);
        }

        // Device certificate XML fragment
        if (rawdevices[i].device_entry.vendor_id == 0x041e) {
            /*
             * This code is currently disabled except for vendors we
             * know does support it: all devices say that
             * they support getting a device certificate but a lot of
             * them obviously doesn't, instead they crash when you try
             * to obtain it.
             */
            ret = LIBMTP_Get_Device_Certificate(device, &devcert);
            if (ret == 0 && devcert != NULL) {
                fprintf(stdout, "\nDevice Certificate:\n%s\n", devcert);
                free(devcert);
            } else {
                fprintf(stdout, "Unable to acquire device certificate, perhaps this device "
                        "does not support this\n");
                LIBMTP_Dump_Errorstack(device);
                LIBMTP_Clear_Errorstack(device);
            }
        }

        /* Try to get Media player device info XML file... */
        /* Loop over storages */
        for (storage = device->storage; storage != 0; storage = storage->next) {
            LIBMTP_file_t *files;

            /* Get file listing for the root directory, no other dirs */
            files = LIBMTP_Get_Files_And_Folders(device,
                                                 storage->id,
                                                 0);

            if (files != NULL) {
                LIBMTP_file_t *file, *tmp;
                file = files;
                while (file != NULL) {
                    if (!strcmp(file->filename, "WMPInfo.xml") ||
                            !strcmp(file->filename, "WMPinfo.xml") ||
                            !strcmp(file->filename, "default-capabilities.xml")) {
                        if (file->item_id != 0) {
                            /* Dump this file */
                            FILE *xmltmp = tmpfile();
                            int tmpfiledescriptor = fileno(xmltmp);

                            if (tmpfiledescriptor != -1) {
                                int ret = LIBMTP_Get_Track_To_File_Descriptor(device,
                                          file->item_id,
                                          tmpfiledescriptor,
                                          NULL,
                                          NULL);
                                if (ret == 0) {
                                    uint8_t *buf = NULL;
                                    uint32_t readbytes;

                                    buf = malloc(XML_BUFSIZE);
                                    if (buf == NULL) {
                                        printf("Could not allocate %08x bytes...\n", XML_BUFSIZE);
                                        LIBMTP_Dump_Errorstack(device);
                                        LIBMTP_Clear_Errorstack(device);
                                        free(rawdevices);
                                        return 1;
                                    }

                                    lseek(tmpfiledescriptor, 0, SEEK_SET);
                                    readbytes = read(tmpfiledescriptor, (void*) buf, XML_BUFSIZE);

                                    if (readbytes >= 2 && readbytes < XML_BUFSIZE) {
                                        fprintf(stdout, "\n%s file contents:\n", file->filename);
                                        dump_xml_fragment(buf, readbytes);
                                    } else {
                                        perror("Unable to read file");
                                        LIBMTP_Dump_Errorstack(device);
                                        LIBMTP_Clear_Errorstack(device);
                                    }
                                    free(buf);
                                } else {
                                    LIBMTP_Dump_Errorstack(device);
                                    LIBMTP_Clear_Errorstack(device);
                                }
                                fclose(xmltmp);
                            }
                        }
                    }
                    tmp = file;
                    file = file->next;
                    LIBMTP_destroy_file_t(tmp);
                }
            }
        }
        LIBMTP_Release_Device(device);
    } /* End For Loop */

    free(rawdevices);

    printf("OK.\n");

    return 0;
}