241 lines
9.9 KiB
C
241 lines
9.9 KiB
C
/**********************************************************************
|
|
* Minolta Dimage V digital camera communication library *
|
|
* Copyright 2000,2001 Gus Hartmann *
|
|
* *
|
|
* This program is free software; you can redistribute it and/or *
|
|
* modify it under the terms of the GNU General Public License as *
|
|
* published by the Free Software Foundation; either version 2 of *
|
|
* the License, or (at your option) any later version. *
|
|
* *
|
|
* This program is distributed in the hope that it will be useful, *
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
|
|
* GNU General Public License for more details. *
|
|
* *
|
|
* You should have received a copy of the GNU General Public *
|
|
* License along with this program; if not, write to the *
|
|
* Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
|
|
* Boston, MA 02110-1301 USA
|
|
* *
|
|
**********************************************************************/
|
|
|
|
/* $Id$ */
|
|
|
|
#if defined HAVE_UNISTD_H
|
|
#include <unistd.h>
|
|
#endif
|
|
|
|
#if defined HAVE_STDIO_H
|
|
#include <stdio.h>
|
|
#endif
|
|
|
|
#if defined HAVE_STDLIB_H
|
|
#include <stdlib.h>
|
|
#endif
|
|
|
|
#if defined HAVE_STRING_H
|
|
#include <string.h>
|
|
#endif
|
|
|
|
#if defined HAVE_SYS_TIME_H
|
|
#include <sys/time.h>
|
|
#endif
|
|
|
|
/* These better be around. */
|
|
#include <gphoto2/gphoto2.h>
|
|
#include <gphoto2/gphoto2-port.h>
|
|
|
|
#define DIMAGEV_VERSION "$Revision$"
|
|
|
|
/* These are the response codes. */
|
|
#define DIMAGEV_STX 0x02
|
|
#define DIMAGEV_ETX 0x03
|
|
#define DIMAGEV_EOT 0x04
|
|
#define DIMAGEV_ACK 0x06
|
|
#define DIMAGEV_NAK 0x15
|
|
#define DIMAGEV_CAN 0x18
|
|
|
|
/* These are the commands. */
|
|
#define DIMAGEV_INQUIRY (unsigned char*)"\x01"
|
|
#define DIMAGEV_DRIVE_READY (unsigned char*)"\x02"
|
|
#define DIMAGEV_GET_DIR (unsigned char*)"\x03"
|
|
#define DIMAGEV_GET_IMAGE (unsigned char*)"\x04"
|
|
#define DIMAGEV_ERASE_IMAGE (unsigned char*)"\x05"
|
|
#define DIMAGEV_ERASE_ALL (unsigned char*)"\x06"
|
|
#define DIMAGEV_GET_STATUS (unsigned char*)"\x07"
|
|
#define DIMAGEV_SET_DATA (unsigned char*)"\x08"
|
|
#define DIMAGEV_GET_DATA (unsigned char*)"\x09"
|
|
#define DIMAGEV_SHUTTER (unsigned char*)"\x0a"
|
|
#define DIMAGEV_FORMAT (unsigned char*)"\x0b"
|
|
#define DIMAGEV_DIAG (unsigned char*)"\x0c"
|
|
#define DIMAGEV_GET_THUMB (unsigned char*)"\x0d"
|
|
#define DIMAGEV_SET_IMAGE (unsigned char*)"\x0e"
|
|
|
|
/* Using five digits is a bit forward-thinking, since I've never even gotten
|
|
enough pictures on a card to fill two digits, but I may as well use all
|
|
the eight.three I can.
|
|
*/
|
|
#define DIMAGEV_FILENAME_FMT "dv%05i.jpg"
|
|
#define DIMAGEV_THUMBNAIL_FMT "dv%05i.ppm"
|
|
|
|
/* These values are needed to convert Y:Cb:Cr image data into RGB. */
|
|
/* Salt as needed. */
|
|
#define CR_COEFF 0.114
|
|
#define CB_COEFF 0.587
|
|
#define Y_COEFF 0.299
|
|
|
|
/* This struct basically is a NULL-safe string; image data and other buffers
|
|
can contain NULLs, and classic C strings won't work.
|
|
*/
|
|
typedef struct {
|
|
int length;
|
|
unsigned char buffer[1024];
|
|
} dimagev_packet;
|
|
|
|
/* This struct represents the information returned by the DIMAGEV_INQUIRY
|
|
command. The response packet payload is 25 bytes, in the order listed
|
|
below. The strings are all ASCII values, e.g. "MINOLTA ". The model is
|
|
always "L1", which was apparently the development name for the Dimage V.
|
|
*/
|
|
typedef struct {
|
|
unsigned char vendor[8];
|
|
unsigned char model[8];
|
|
unsigned char hardware_rev[4];
|
|
unsigned char firmware_rev[4];
|
|
unsigned char have_storage;
|
|
} dimagev_info_t;
|
|
|
|
/* This struct represents the information returned by the DIMAGEV_GET_STATUS
|
|
command. This information is all wedged into seven bytes, as shown here:
|
|
|
|
bits
|
|
|-- 7 --|-- 6 --|-- 5 --|-- 4 --|-- 3 --|-- 2 --|-- 1 --|-- 0 --|
|
|
byte |---------------------------------------------------------------|
|
|
0 | Battery level |
|
|
1 | Number of images (most significant byte) |
|
|
2 | Number of images (least significant byte) |
|
|
3 | Minimum number of images left to take (most significant byte) |
|
|
4 | Minimum number of images left to take (least significant byte)|
|
|
5 | 0 | Busy | 0 | Flash | Lens Status | Card Status |
|
|
6 | Camera and Card ID number |
|
|
|---------------------------------------------------------------|
|
|
|
|
Battery level: 0x00 == "not enough", 0xff == "enough"
|
|
Lens status: 00 == normal, 01|10 == doesn't match flash, 11 == detached
|
|
Card status: 00 == normal, 01 == full, 10 == write-protected, 11 == bad
|
|
Flash: 1 == charging, 0 == ready
|
|
|
|
I could probably have left it in one of these compacted structures, but
|
|
memory is not so expensive as to spend that much effort shifting bits.
|
|
*/
|
|
typedef struct {
|
|
unsigned char battery_level;
|
|
unsigned int number_images;
|
|
unsigned int minimum_images_can_take;
|
|
unsigned char busy;
|
|
unsigned char flash_charging;
|
|
unsigned char lens_status;
|
|
unsigned char card_status;
|
|
unsigned char id_number;
|
|
} dimagev_status_t;
|
|
|
|
/* This struct represents the information returned by the DIMAGEV_GET_DATA
|
|
command and sent with the DIMAGEV_SET_DATA command. It's another tightly
|
|
packed bit field, as described below:
|
|
|
|
bits
|
|
|-- 7 --|-- 6 --|-- 5 --|-- 4 --|-- 3 --|-- 2 --|-- 1 --|-- 0 --|
|
|
byte |---------------------------------------------------------------|
|
|
0 | hmode | OR | Date | Self | Flash |Quality| Rec |
|
|
1 | Camera Clock (year) |
|
|
2 | Camera Clock (month) |
|
|
3 | Camera Clock (day) |
|
|
4 | Camera Clock (hour) |
|
|
5 | Camera Clock (minute) |
|
|
6 | Camera Clock (second) |
|
|
7 | Exposure correction data |
|
|
8 | valid | Camera and Card ID number |
|
|
|---------------------------------------------------------------|
|
|
|
|
hmode: "host mode" e.g. if the PC or camera is in control.
|
|
OR: Exposure correction data field is valid - used only for SET command.
|
|
Date: The date information is valid - used only for SET command.
|
|
Self: True if camera is in self-timer mode.
|
|
Flash: 00 == Auto, 01 == Force Flash, 10==No Flash, 11 == Invalid
|
|
Quality: Compression setting, 1 == Fine, 0 == Standard
|
|
Record mode: When setting, 1 == turn on LCD viewfinder.
|
|
When getting, 1 == switch in record mode.
|
|
Camera Clock: BCD two-digit values for times. Hours are military 0-23.
|
|
Exposure correction data: sets exposure correction, from -127 to 128.
|
|
valid: Used to set "valid" for memory cards.
|
|
Camera and Card ID: used when switching cards.
|
|
*/
|
|
typedef struct {
|
|
unsigned char host_mode;
|
|
unsigned char exposure_valid;
|
|
unsigned char date_valid;
|
|
unsigned char self_timer_mode;
|
|
unsigned char flash_mode;
|
|
unsigned char quality_setting;
|
|
unsigned char play_rec_mode;
|
|
unsigned char year;
|
|
unsigned char month;
|
|
unsigned char day;
|
|
unsigned char hour;
|
|
unsigned char minute;
|
|
unsigned char second;
|
|
unsigned char exposure_correction;
|
|
unsigned char valid;
|
|
unsigned char id_number;
|
|
} dimagev_data_t;
|
|
|
|
/* This struct is used as the camera->camlib_data value in this library. */
|
|
typedef struct _CameraPrivateLibrary {
|
|
int size;
|
|
GPPort *dev;
|
|
dimagev_data_t *data;
|
|
dimagev_status_t *status;
|
|
dimagev_info_t *info;
|
|
} dimagev_t;
|
|
|
|
/* These functions are in packet.c */
|
|
dimagev_packet *dimagev_make_packet(const unsigned char *const buffer, unsigned int length, unsigned int seq);
|
|
dimagev_packet *dimagev_read_packet(dimagev_t *dimagev);
|
|
int dimagev_verify_packet(dimagev_packet *p);
|
|
dimagev_packet *dimagev_strip_packet(dimagev_packet *p);
|
|
void dimagev_dump_packet(dimagev_packet *p);
|
|
unsigned char dimagev_decimal_to_bcd(unsigned char decimal);
|
|
unsigned char dimagev_bcd_to_decimal(unsigned char bcd);
|
|
int dimagev_packet_sequence(dimagev_packet *p);
|
|
|
|
/* These functions are in data.c */
|
|
int dimagev_send_data(dimagev_t *dimagev);
|
|
int dimagev_get_camera_data(dimagev_t *dimagev);
|
|
dimagev_data_t *dimagev_import_camera_data(unsigned char *raw_data);
|
|
unsigned char *dimagev_export_camera_data(dimagev_data_t *good_data);
|
|
void dimagev_dump_camera_data(dimagev_data_t *data);
|
|
int dimagev_set_date(dimagev_t *dimagev);
|
|
|
|
/* These functions are in status.c */
|
|
int dimagev_get_camera_status(dimagev_t *dimagev);
|
|
dimagev_status_t *dimagev_import_camera_status(unsigned char *raw_data);
|
|
void dimagev_dump_camera_status(dimagev_status_t *status);
|
|
|
|
/* These functions are in info.c */
|
|
int dimagev_get_camera_info(dimagev_t *dimagev);
|
|
dimagev_info_t *dimagev_import_camera_info(unsigned char *raw_data);
|
|
void dimagev_dump_camera_info(dimagev_info_t *info);
|
|
|
|
/* These functions are in capture.c */
|
|
int dimagev_shutter(dimagev_t *dimagev);
|
|
|
|
/* These functions are in upload.c */
|
|
int dimagev_put_file(dimagev_t* dimagev, CameraFile *file);
|
|
|
|
/* These functions are in util.c */
|
|
int dimagev_get_picture(dimagev_t *dimagev, int file_number, CameraFile *file);
|
|
int dimagev_delete_picture(dimagev_t *dimagev, int file_number);
|
|
int dimagev_delete_all(dimagev_t *dimagev);
|
|
int dimagev_get_thumbnail(dimagev_t *dimagev, int file_number, CameraFile *file);
|
|
unsigned char *dimagev_ycbcr_to_ppm(unsigned char *ycbcr);
|