Source code upload
[framework/connectivity/libgphoto2.git] / camlibs / panasonic / dc1580.c
1 /*
2         Copyright © 2000 Mariusz Zynel <mariusz@mizar.org> (gPhoto port)
3         Copyright © 2000 Fredrik Roubert <roubert@df.lth.se> (idea)
4         Copyright © 1999 Galen Brooks <galen@nine.com> (DC1580 code)
5
6         This file is part of the gPhoto project and may only be used,  modified,
7         and distributed under the terms of the gPhoto project license,  COPYING.
8         By continuing to use, modify, or distribute  this file you indicate that
9         you have read the license, understand and accept it fully.
10
11         THIS  SOFTWARE IS PROVIDED AS IS AND COME WITH NO WARRANTY  OF ANY KIND,
12         EITHER  EXPRESSED OR IMPLIED.  IN NO EVENT WILL THE COPYRIGHT  HOLDER BE
13         LIABLE FOR ANY DAMAGES RESULTING FROM THE USE OF THIS SOFTWARE.
14
15         Note:
16
17         This is a Panasonic PV/NV-DC1580 camera gPhoto library source code.
18
19         An algorithm  for  checksums  borrowed  from  Michael McCormack's  Nikon
20         CoolPix 600 library for gPhoto1.
21 */
22
23 #include "config.h"
24
25 #include <stdlib.h>
26 #include <stdarg.h>
27 #include <sys/time.h>
28 #include <sys/stat.h>
29 #include <unistd.h>
30 #ifdef HAVE_MEMORY_H
31 #include <memory.h>
32 #endif
33 #include <string.h>
34
35 #ifdef ENABLE_NLS
36 #  include <libintl.h>
37 #  undef _
38 #  define _(String) dgettext (GETTEXT_PACKAGE, String)
39 #  ifdef gettext_noop
40 #    define N_(String) gettext_noop (String)
41 #  else
42 #    define N_(String) (String)
43 #  endif
44 #else
45 #  define _(String) (String)
46 #  define N_(String) (String)
47 #endif
48
49 #include "dc.h"
50 #include "dc1580.h"
51
52 #ifndef __FILE__
53 #  define __FILE__ "dc1580.c"
54 #endif
55
56 #define GP_MODULE "dc1580"
57
58 /******************************************************************************/
59
60 /* Internal utility functions */
61
62 /* dsc2_checksum - establish checksum for size bytes in buffer */
63
64 static uint8_t dsc2_checksum(char *buffer, int size) {
65
66         int     checksum = 0;
67         int     i;
68
69         for (i = 1; i < size - 2; i++) {
70                 checksum += buffer[i];
71                 checksum %= 0x100;
72         }
73
74         return checksum;
75 }
76
77 /* dsc2_sendcmd - send command with data to DSC */
78
79 static int dsc2_sendcmd(Camera *camera, uint8_t cmd, long int data, uint8_t sequence) {
80
81         int     i;
82
83         DEBUG_PRINT_MEDIUM(("Sending command: 0x%02x, data: %i, sequence: %i.", cmd, data, sequence));
84
85         memset(camera->pl->buf, 0, 16);
86
87         camera->pl->buf[0] = 0x08;
88         camera->pl->buf[1] = sequence;
89         camera->pl->buf[2] = 0xff - sequence;
90         camera->pl->buf[3] = cmd;
91
92         for (i = 0; i < sizeof(data); i++)
93                 camera->pl->buf[4 + i] = (uint8_t)(data >> 8*i);
94
95         camera->pl->buf[14] = dsc2_checksum(camera->pl->buf, 16);
96
97         return gp_port_write(camera->port, camera->pl->buf, 16);
98 }
99
100 /* dsc2_retrcmd - retrieve command and its data from DSC */
101
102 static int dsc2_retrcmd(Camera *camera) {
103         
104         int     result = GP_ERROR;
105         int     s;
106
107         if ((s = gp_port_read(camera->port, camera->pl->buf, 16)) == GP_ERROR)
108                 return GP_ERROR;
109
110 /*      Make sense in debug only. Done on gp_port level.
111         if (0 < s)
112                 dsc_dumpmem(camera->pl->buf, s);
113
114 */
115         if (s != 16 ||  camera->pl->buf[DSC2_BUF_BASE] != 0x08 ||
116                         camera->pl->buf[DSC2_BUF_SEQ] != 0xff - (uint8_t)camera->pl->buf[DSC2_BUF_SEQC]) {
117                 RETURN_ERROR(EDSCBADRSP);
118                 /* bad response */
119         }
120         else
121                 result = camera->pl->buf[DSC2_BUF_CMD];
122
123         DEBUG_PRINT_MEDIUM(("Retrieved command: %i.", result));
124
125         return result;
126 }
127
128 /* dsc2_connect - try hand shake with camera and establish connection */
129
130 static int dsc2_connect(Camera *camera, int speed) {
131         
132         DEBUG_PRINT_MEDIUM(("Connecting camera with speed: %i.", speed));
133
134         if (dsc1_setbaudrate(camera, speed) != GP_OK)
135                 return GP_ERROR;
136
137         if (dsc1_getmodel(camera) != DSC2)
138                 RETURN_ERROR(EDSCBADDSC);
139                 /* bad camera model */
140
141         if (dsc2_sendcmd(camera, DSC2_CMD_CONNECT, 0, 0) != GP_OK)
142                 return GP_ERROR;
143
144         if (dsc2_retrcmd(camera) != DSC2_RSP_OK)
145                 RETURN_ERROR(EDSCBADRSP);
146                 /* bad response */
147
148         DEBUG_PRINT_MEDIUM(("Camera connected successfully."));
149
150         return GP_OK;
151 }
152
153 /* dsc2_disconnect - reset camera, free buffers and close files */
154
155 static int dsc2_disconnect(Camera *camera) {
156         
157         DEBUG_PRINT_MEDIUM(("Disconnecting the camera."));
158
159         if (dsc2_sendcmd(camera, DSC2_CMD_RESET, 0, 0) != GP_OK)
160                 return GP_ERROR;
161
162         if (dsc2_retrcmd(camera) != DSC2_RSP_OK)
163                 RETURN_ERROR(EDSCBADRSP)
164                 /* bad response */
165         else
166                 sleep(DSC_PAUSE); /* let camera to redraw its screen */
167
168         DEBUG_PRINT_MEDIUM(("Camera disconnected."));
169
170         return GP_OK;
171 }
172
173 /* dsc2_getindex - retrieve the number of images stored in camera memory */
174
175 static int dsc2_getindex(Camera *camera) {
176         
177         int     result = GP_ERROR;
178
179         DEBUG_PRINT_MEDIUM(("Retrieving the number of images."));
180
181         if (dsc2_sendcmd(camera, DSC2_CMD_GET_INDEX, 0, 0) != GP_OK)
182                 return GP_ERROR;
183
184         if (dsc2_retrcmd(camera) == DSC2_RSP_INDEX)
185                 result =
186                         ((uint32_t)camera->pl->buf[DSC2_BUF_DATA]) |
187                         ((uint8_t)camera->pl->buf[DSC2_BUF_DATA + 1] << 8) |
188                         ((uint8_t)camera->pl->buf[DSC2_BUF_DATA + 2] << 16) |
189                         ((uint8_t)camera->pl->buf[DSC2_BUF_DATA + 3] << 24);
190         else
191                 RETURN_ERROR(EDSCBADRSP);
192                 /* bad response */
193
194         DEBUG_PRINT_MEDIUM(("Number of images: %i", result));
195
196         return result;
197 }
198
199 /* dsc2_delete - delete image #index from camera memory */
200
201 static int dsc2_delete(Camera *camera, int index) {
202         
203         DEBUG_PRINT_MEDIUM(("Deleting image: %i.", index));
204
205         if (index < 1)
206                 RETURN_ERROR(EDSCBADNUM);
207                 /* bad image number */
208
209         if (dsc2_sendcmd(camera, DSC2_CMD_DELETE, index, 0) != GP_OK)
210                 return GP_ERROR;
211
212         if (dsc2_retrcmd(camera) != DSC2_RSP_OK)
213                 RETURN_ERROR(EDSCBADRSP);
214                 /* bad response */
215
216         DEBUG_PRINT_MEDIUM(("Image: %i deleted.", index));
217         return GP_OK;
218 }
219
220 /* dsc2_selectimage - select image to download, return its size */
221
222 static int dsc2_selectimage(Camera *camera, int index, int thumbnail) {
223         
224         int     size = 0;
225
226         DEBUG_PRINT_MEDIUM(("Selecting image: %i, thumbnail: %i.", index, thumbnail));
227
228         if (index < 1)
229                 RETURN_ERROR(EDSCBADNUM);
230                 /* bad image number */
231
232         if (thumbnail == DSC_THUMBNAIL) {
233                 if (dsc2_sendcmd(camera, DSC2_CMD_THUMB, index, 0) != GP_OK)
234                         return GP_ERROR;
235         } else {
236                 if (dsc2_sendcmd(camera, DSC2_CMD_SELECT, index, 0) != GP_OK)
237                         return GP_ERROR;
238         }
239
240         if (dsc2_retrcmd(camera) != DSC2_RSP_IMGSIZE)
241                 RETURN_ERROR(EDSCBADRSP);
242                 /* bad response */
243
244         size =  ((uint32_t)camera->pl->buf[DSC2_BUF_DATA]) |
245                 ((uint8_t)camera->pl->buf[DSC2_BUF_DATA + 1] << 8) |
246                 ((uint8_t)camera->pl->buf[DSC2_BUF_DATA + 2] << 16) |
247                 ((uint8_t)camera->pl->buf[DSC2_BUF_DATA + 3] << 24);
248
249         DEBUG_PRINT_MEDIUM(("Selected image: %i, thumbnail: %i, size: %i.", index, thumbnail, size));
250
251         return size;
252 }
253
254 /* gp_port_readimageblock - read #block block (1024 bytes) of an image into buf */
255
256 static int dsc2_readimageblock(Camera *camera, int block, char *buffer) {
257         
258         DEBUG_PRINT_MEDIUM(("Reading image block: %i.", block));
259
260         if (dsc2_sendcmd(camera, DSC2_CMD_GET_DATA, block, block) != GP_OK)
261                 return GP_ERROR;
262
263         if (gp_port_read(camera->port, camera->pl->buf, DSC_BUFSIZE) != DSC_BUFSIZE)
264                 RETURN_ERROR(EDSCBADRSP);
265                 /* bad response */
266
267         if ((uint8_t)camera->pl->buf[0] != 1 ||
268                         (uint8_t)camera->pl->buf[1] != block ||
269                         (uint8_t)camera->pl->buf[2] != 0xff - block ||
270                         (uint8_t)camera->pl->buf[3] != DSC2_RSP_DATA ||
271                         (uint8_t)camera->pl->buf[DSC_BUFSIZE - 2] != dsc2_checksum(camera->pl->buf, DSC_BUFSIZE))
272                 RETURN_ERROR(EDSCBADRSP);
273                 /* bad response */
274
275         if (buffer)
276                 memcpy(buffer, &camera->pl->buf[4], DSC_BLOCKSIZE);
277
278         DEBUG_PRINT_MEDIUM(("Block: %i read in.", block));
279
280         return DSC_BLOCKSIZE;
281 }
282
283 /* dsc2_readimage - read #index image or thumbnail and return its contents */
284
285 #if 0
286 static char *dsc2_readimage(Camera *camera, int index, int thumbnail, int *size) {
287
288         char    kind[16];
289         int     blocks, i;
290         char    *buffer = NULL;
291
292         DEBUG_PRINT_MEDIUM(("Reading image: %i, thumbnail: %i.", index, thumbnail));
293
294         if ((*size = dsc2_selectimage(camera, index, thumbnail)) < 0)
295                 return NULL;
296
297         if (thumbnail == DSC_THUMBNAIL)
298                 strcpy(kind, "thumbnail");
299         else
300                 strcpy(kind, "image");
301
302         if (!(buffer = (char*)malloc(*size))) {
303                 DEBUG_PRINT_MEDIUM(("Failed to allocate memory for %s data.", kind));
304                 return NULL;
305         }
306
307         blocks = (*size - 1)/DSC_BLOCKSIZE + 1;
308
309         for (i = 0; i < blocks; i++) {
310                 if (dsc2_readimageblock(camera, i, &buffer[i*DSC_BLOCKSIZE]) == GP_ERROR) {
311                         DEBUG_PRINT_MEDIUM(("Error during %s transfer.", kind));
312                         free(buffer);
313                         return NULL;
314                 }
315         }
316
317         DEBUG_PRINT_MEDIUM(("Image: %i read in.", index));
318
319         return buffer;
320 }
321 #endif
322
323 /* dsc2_setimagesize - set size of an image to upload to camera */
324
325 static int dsc2_setimagesize(Camera *camera, int size) {
326
327         DEBUG_PRINT_MEDIUM(("Setting image size to: %i.", size));
328
329         if (dsc2_sendcmd(camera, DSC2_CMD_SET_SIZE, size, 0) != GP_OK)
330                 return GP_ERROR;
331
332         if (dsc2_retrcmd(camera) != DSC2_RSP_OK)
333                 RETURN_ERROR(EDSCBADRSP);
334                 /* bad response */
335
336         DEBUG_PRINT_MEDIUM(("Image size set to: %i.", size));
337
338         return GP_OK;
339 }
340
341 /* gp_port_writeimageblock - write size bytes from buffer rounded to 1024 bytes to camera */
342
343 static int dsc2_writeimageblock(Camera *camera, int block, char *buffer, int size) {
344
345         DEBUG_PRINT_MEDIUM(("Writing image block: %i.", block));
346
347         memset(camera->pl->buf, 0, DSC_BUFSIZE);
348
349         camera->pl->buf[0] = 0x01;
350         camera->pl->buf[1] = block;
351         camera->pl->buf[2] = 0xff - block;
352         camera->pl->buf[3] = DSC2_CMD_SEND_DATA;
353
354         if (DSC_BLOCKSIZE < size)
355                 size = DSC_BLOCKSIZE;
356
357         memcpy(&camera->pl->buf[4], buffer, size);
358
359         camera->pl->buf[DSC_BUFSIZE - 2] = dsc2_checksum(camera->pl->buf, DSC_BUFSIZE);
360
361         if (gp_port_write(camera->port, camera->pl->buf, DSC_BUFSIZE) != GP_OK)
362                 return GP_ERROR;
363
364         if (dsc2_retrcmd(camera) != DSC2_RSP_OK)
365                 RETURN_ERROR(EDSCBADRSP);
366                 /* bad response */
367
368         DEBUG_PRINT_MEDIUM(("Block: %i of size: %i written.", block, size));
369
370         return GP_OK;
371 }
372
373 /* dsc2_writeimage - write an image to camera memory, size bytes at buffer */
374
375 #if 0
376 static int dsc2_writeimage(Camera *camera, char *buffer, int size) {
377         
378         int     blocks, blocksize, i;
379
380         DEBUG_PRINT_MEDIUM(("Writing an image of size: %i.", size));
381
382         if ((dsc2_setimagesize(camera, size)) != GP_OK)
383                 return GP_ERROR;
384
385         blocks = (size - 1)/DSC_BLOCKSIZE + 1;
386
387         for (i = 0; i < blocks; i++) {
388                 blocksize = size - i*DSC_BLOCKSIZE;
389                 if (DSC_BLOCKSIZE < blocksize)
390                         blocksize = DSC_BLOCKSIZE;
391                 if (dsc2_writeimageblock(camera, i, &buffer[i*DSC_BLOCKSIZE], blocksize) != GP_OK) {
392                         DEBUG_PRINT_MEDIUM(("Error during image transfer."));
393                         return GP_ERROR;
394                 }
395         }
396
397         DEBUG_PRINT_MEDIUM(("Image written successfully."));
398
399         return GP_OK;
400 }
401 #endif
402
403 /* dsc2_preview - show selected image on camera's LCD  */
404
405 #if 0
406 static int dsc2_preview(Camera *camera, int index) {
407         
408         if (index < 1)
409                 RETURN_ERROR(EDSCBADNUM);
410                 /* bad image number */
411
412         if (dsc2_sendcmd(camera, DSC2_CMD_PREVIEW, index, 0) != GP_OK)
413                 return GP_ERROR;
414
415         if (dsc2_retrcmd(camera) != DSC2_RSP_OK)
416                 RETURN_ERROR(EDSCBADRSP);
417                 /* bad response */
418
419         return GP_OK;
420 }
421 #endif
422
423 /******************************************************************************/
424
425 /* Library interface functions */
426
427 int camera_id (CameraText *id) {
428         
429         strcpy(id->text, "panasonic-dc1580");
430
431         return (GP_OK);
432 }
433
434 int camera_abilities (CameraAbilitiesList *list) {
435         
436         CameraAbilities a;
437         char    *models[] = {
438                         "Panasonic:DC1580",
439                         "Nikon:CoolPix 600",
440                         NULL };
441         int     i = 0, result;
442         
443         while (models[i]) {
444                 memset(&a, 0, sizeof(a));
445                 a.status = GP_DRIVER_STATUS_PRODUCTION;
446                 strcpy(a.model, models[i]);
447                 a.port         = GP_PORT_SERIAL;
448                 a.speed[0]     = 9600;
449                 a.speed[1]     = 19200;
450                 a.speed[2]     = 38400;
451                 a.speed[3]     = 57600;
452                 a.speed[4]     = 115200;
453                 a.speed[5]     = 0;
454                 a.operations        =   GP_OPERATION_NONE;
455                 a.file_operations   =   GP_FILE_OPERATION_DELETE | 
456                                         GP_FILE_OPERATION_PREVIEW;
457                 a.folder_operations =   GP_FOLDER_OPERATION_PUT_FILE;
458
459                 CHECK (gp_abilities_list_append(list, a));
460                 i++;
461         }
462
463         return GP_OK;
464 }
465
466 static int camera_exit (Camera *camera, GPContext *context) {
467         gp_context_status(context, _("Disconnecting camera."));
468         dsc2_disconnect(camera);
469         if (camera->pl->buf) {
470                 free (camera->pl->buf);
471                 camera->pl->buf = NULL;
472         }
473         free (camera->pl);
474         camera->pl = NULL;
475         return (GP_OK);
476 }
477
478 static int file_list_func (CameraFilesystem *fs, const char *folder,
479                            CameraList *list, void *data, GPContext *context) {
480
481         Camera  *camera = data;
482         int     count, result;
483         
484         CHECK (count = dsc2_getindex(camera));
485         
486         CHECK (gp_list_populate(list, DSC_FILENAMEFMT, count));
487
488         return GP_OK;
489 }
490
491 static int get_info_func (CameraFilesystem *fs, const char *folder,
492                           const char *filename, CameraFileInfo *info,
493                           void *data, GPContext *context) {
494
495         Camera  *camera = data;
496         int     index, result;
497
498         /* index is the 0-based image number on the camera */
499         CHECK (index = gp_filesystem_number(camera->fs, folder, filename, context));
500         index++;
501
502         info->file.fields = GP_FILE_INFO_TYPE | GP_FILE_INFO_NAME | GP_FILE_INFO_SIZE;
503         strcpy(info->file.type, GP_MIME_JPEG);
504         sprintf(info->file.name, DSC_FILENAMEFMT, index);
505         info->file.size = dsc2_selectimage(camera, index, DSC_FULLIMAGE);
506
507         info->preview.fields = GP_FILE_INFO_TYPE | GP_FILE_INFO_NAME | GP_FILE_INFO_SIZE;
508         strcpy(info->preview.type, GP_MIME_JPEG);
509         info->preview.size = dsc2_selectimage(camera, index, DSC_THUMBNAIL);
510
511         return GP_OK;
512 }
513
514 static int get_file_func (CameraFilesystem *fs, const char *folder,
515                           const char *filename, CameraFileType type,
516                           CameraFile *file, void *data, GPContext *context) {
517
518         Camera *camera = data;
519         int     index, i, size, blocks, result;
520         unsigned int id;
521
522         gp_context_status(context, _("Downloading %s."), filename);
523
524         /* index is the 0-based image number on the camera */
525         CHECK (index = gp_filesystem_number(camera->fs, folder, filename, context));
526         index++;
527
528         switch (type) {
529         case GP_FILE_TYPE_PREVIEW:
530                 size = dsc2_selectimage(camera, index, DSC_THUMBNAIL);
531                 break;
532         case GP_FILE_TYPE_NORMAL:
533                 size = dsc2_selectimage(camera, index, DSC_FULLIMAGE);
534                 break;
535         default:
536                 return (GP_ERROR_NOT_SUPPORTED);
537         }
538         if (size < 0)
539                 return (size);
540
541         CHECK (gp_file_set_name(file, filename));
542         CHECK (gp_file_set_mime_type(file, GP_MIME_JPEG));
543
544         blocks = (size - 1)/DSC_BLOCKSIZE + 1;
545
546         id = gp_context_progress_start (context, blocks, _("Getting data..."));
547         for (i = 0; i < blocks; i++) {
548                 CHECK (dsc2_readimageblock(camera, i, NULL));
549                 CHECK (gp_file_append(file, &camera->pl->buf[4], DSC_BLOCKSIZE));
550                 gp_context_progress_update (context, id, i + 1);
551                 if (gp_context_cancel (context) == GP_CONTEXT_FEEDBACK_CANCEL)
552                         return (GP_ERROR_CANCEL);
553         }
554         gp_context_progress_stop (context, id);
555
556         return GP_OK;
557 }
558
559 static int put_file_func (CameraFilesystem *fs, const char *folder,
560                           CameraFile *file, void *user_data,
561                           GPContext *context) {
562         
563         Camera *camera = user_data;
564         int             blocks, blocksize, i, result;
565         const char      *name;
566         const char      *data;
567         long int        size;
568         unsigned int id;
569
570         gp_file_get_name(file, &name);
571         gp_context_status(context, _("Uploading image: %s."), name);
572
573 /*      We can not figure out file type, at least by now.
574
575         if (strcmp(file->type, "image/jpg") != 0) {
576                 dsc_print_message(camera, "JPEG image format allowed only.");
577                 return GP_ERROR;
578         }
579 */
580         gp_file_get_data_and_size (file, &data, &size);
581         if (size > DSC_MAXIMAGESIZE) {
582                 gp_context_message (context, _("File size is %ld bytes. "
583                                    "The size of the largest file possible to "
584                                    "upload is: %i bytes."), size, 
585                                    DSC_MAXIMAGESIZE);
586                 return GP_ERROR;
587         }
588
589         if ((result = dsc2_setimagesize(camera, size)) != GP_OK) return result;
590
591         blocks = (size - 1)/DSC_BLOCKSIZE + 1;
592
593         id = gp_context_progress_start (context, blocks, _("Uploading..."));
594         for (i = 0; i < blocks; i++) {
595                 blocksize = size - i*DSC_BLOCKSIZE;
596                 if (DSC_BLOCKSIZE < blocksize)
597                         blocksize = DSC_BLOCKSIZE;
598                 result = dsc2_writeimageblock(camera, i, 
599                                                (char*)&data[i*DSC_BLOCKSIZE], 
600                                                blocksize);
601                 if (result != GP_OK)
602                         return result;
603                 gp_context_progress_update (context, id, i + 1);
604                 if (gp_context_cancel (context) == GP_CONTEXT_FEEDBACK_CANCEL)
605                         return (GP_ERROR_CANCEL);
606         }
607         gp_context_progress_stop (context, id);
608
609         return GP_OK;
610 }
611
612 static int delete_file_func (CameraFilesystem *fs, const char *folder,
613                              const char *filename, void *data,
614                              GPContext *context) {
615         
616         Camera *camera = data;
617         int     index, result;
618
619         gp_context_status(context, _("Deleting image %s."), filename);
620
621         /* index is the 0-based image number on the camera */
622         CHECK (index = gp_filesystem_number (camera->fs, folder, filename, context));
623         index++;
624
625         return dsc2_delete(camera, index);
626 }
627
628 static int camera_about (Camera *camera, CameraText *about, GPContext *context) 
629 {
630         strcpy(about->text,
631                         _("Panasonic DC1580 gPhoto2 library\n"
632                         "Mariusz Zynel <mariusz@mizar.org>\n\n"
633                         "Based on dc1000 program written by\n"
634                         "Fredrik Roubert <roubert@df.lth.se> and\n"
635                         "Galen Brooks <galen@nine.com>."));
636         return (GP_OK);
637 }
638
639 static CameraFilesystemFuncs fsfuncs = {
640         .file_list_func = file_list_func,
641         .get_info_func = get_info_func,
642         .get_file_func = get_file_func,
643         .put_file_func = put_file_func,
644         .del_file_func = delete_file_func,
645 };
646
647 int camera_init (Camera *camera, GPContext *context) 
648 {
649         GPPortSettings settings;
650         int result, selected_speed;
651
652         /* First, set up all the function pointers */
653         camera->functions->exit                 = camera_exit;
654         camera->functions->about                = camera_about;
655
656         camera->pl = malloc (sizeof (CameraPrivateLibrary));
657         if (!camera->pl)
658                 return (GP_ERROR_NO_MEMORY);
659         camera->pl->buf = malloc (sizeof (char) * DSC_BUFSIZE);
660         if (!camera->pl->buf) {
661                 free (camera->pl);
662                 camera->pl = NULL;
663                 return (GP_ERROR_NO_MEMORY);
664         }
665
666         CHECK (gp_port_set_timeout (camera->port, 5000));
667
668         /* Configure the port (and remember the speed) */
669         CHECK (gp_port_get_settings (camera->port, &settings));
670         selected_speed = settings.serial.speed;
671         settings.serial.speed      = 9600; /* hand shake speed */
672         settings.serial.bits       = 8;
673         settings.serial.parity     = 0;
674         settings.serial.stopbits   = 1;
675         CHECK (gp_port_set_settings (camera->port, settings));
676
677         CHECK (gp_filesystem_set_funcs (camera->fs, &fsfuncs, camera));
678         /* Connect with the selected speed */
679         return dsc2_connect(camera, selected_speed);
680 }
681
682 /* End of dc1580.c */