CHDK_DE Vorschauversion  Trunk Rev. 5298
 Alle Datenstrukturen Dateien Funktionen Variablen Typdefinitionen Aufzählungen Aufzählungswerte Makrodefinitionen
ptp.c-Dateireferenz
#include "platform.h"
#include "camera_info.h"
#include "stddef.h"
#include "stdlib.h"
#include "keyboard.h"
#include "ptp_chdk.h"
#include "core.h"
#include "task.h"
#include "script.h"
#include "action_stack.h"
#include "live_view.h"
#include "meminfo.h"
#include "modules.h"
#include "callfunc.h"
#include "remotecap_core.h"
+ Include-Abhängigkeitsdiagramm für ptp.c:

gehe zum Quellcode dieser Datei

Datenstrukturen

struct  recv_ptp_data_state_t
 
struct  send_ptp_data_buf_t
 
struct  ptp_script_msg_q
 

Makrodefinitionen

#define PTP_SCRIPT_MSG_Q_LEN   16
 

Funktionen

int get_ptp_file_buf_size (void)
 
char * get_ptp_file_buf (void)
 
static int handle_ptp (int h, ptp_data *data, int opcode, int sess_id, int trans_id, int param1, int param2, int param3, int param4, int param5)
 
static void init_chdk_ptp ()
 
void init_chdk_ptp_task ()
 
static int recv_ptp_data_init (recv_ptp_data_state_t *rs, int total_size, char *dst_buf)
 
static int recv_ptp_data_chunk (recv_ptp_data_state_t *rs, ptp_data *data)
 
static void recv_ptp_data_finish (recv_ptp_data_state_t *rs)
 
static int recv_ptp_data (ptp_data *data, char *buf, int size)
 
static void flush_recv_ptp_data (ptp_data *data, int size)
 
static int send_ptp_data_buf_init (send_ptp_data_buf_t *sb, int total_size)
 
static void send_ptp_data_buf_free (send_ptp_data_buf_t *sb)
 
static int send_ptp_data (ptp_data *data, const char *src, int size)
 
static int send_ptp_data_buffered (ptp_data *data, void *(*copy_fn)(void *d, const void *s, long sz), const char *src, int size)
 
unsigned script_msg_q_next (unsigned i)
 
unsigned script_msg_q_full (ptp_script_msg_q *q)
 
unsigned script_msg_q_empty (ptp_script_msg_q *q)
 
int enqueue_script_msg (ptp_script_msg_q *q, ptp_script_msg *msg)
 
ptp_script_msgdequeue_script_msg (ptp_script_msg_q *q)
 
void empty_script_msg_q (ptp_script_msg_q *q)
 
ptp_script_msgptp_script_create_msg (unsigned type, unsigned subtype, unsigned datasize, const void *data)
 
int ptp_script_write_msg (ptp_script_msg *msg)
 
ptp_script_msgptp_script_read_msg (void)
 
int ptp_script_write_error_msg (unsigned errtype, const char *err)
 
void start_ptp_script ()
 
static long script_start_ptp (char *script)
 

Variablen

static unsigned script_run_id
 
ptp_script_msg_q msg_q_in
 
ptp_script_msg_q msg_q_out
 
static char * ptp_script = 0
 
static int ptp_script_state = 0
 

Makro-Dokumentation

#define PTP_SCRIPT_MSG_Q_LEN   16

Definiert in Zeile 300 der Datei ptp.c.

Dokumentation der Funktionen

ptp_script_msg* dequeue_script_msg ( ptp_script_msg_q q)

Definiert in Zeile 339 der Datei ptp.c.

339  {
340  ptp_script_msg *msg;
341  if(script_msg_q_empty(q)) {
342  return NULL;
343  }
344  msg = q->q[q->r];
345  q->r = script_msg_q_next(q->r);
346  return msg;
347 }
void empty_script_msg_q ( ptp_script_msg_q q)

Definiert in Zeile 350 der Datei ptp.c.

350  {
351  ptp_script_msg *msg;
352  while((msg = dequeue_script_msg(q))) {
353  free(msg);
354  }
355 }
int enqueue_script_msg ( ptp_script_msg_q q,
ptp_script_msg msg 
)

Definiert in Zeile 326 der Datei ptp.c.

326  {
327  unsigned w = script_msg_q_next(q->w);
328  if(w == q->r) {
329  return 0;
330  }
331  if(msg == NULL) {
332  return 0;
333  }
334  q->q[q->w] = msg;
335  q->w = w;
336  return 1;
337 }
static void flush_recv_ptp_data ( ptp_data data,
int  size 
)
static

Definiert in Zeile 193 der Datei ptp.c.

193  {
194  recv_ptp_data(data,NULL,size);
195 }
char* get_ptp_file_buf ( void  )
int get_ptp_file_buf_size ( void  )
static int handle_ptp ( int  h,
ptp_data data,
int  opcode,
int  sess_id,
int  trans_id,
int  param1,
int  param2,
int  param3,
int  param4,
int  param5 
)
static

Definiert in Zeile 439 der Datei ptp.c.

442 {
443  static union {
444  char *str;
445  } temp_data;
446  static int temp_data_kind = 0; // 0: nothing, 1: ascii string
447  static int temp_data_extra; // size (ascii string)
448  PTPContainer ptp;
449 
450  // initialise default response
451  memset(&ptp,0,sizeof(PTPContainer));
452  ptp.code = PTP_RC_OK;
453  ptp.sess_id = sess_id;
454  ptp.trans_id = trans_id;
455  ptp.num_param = 0;
456 
457  // handle command
458  switch ( param1 )
459  {
460 
461  case PTP_CHDK_Version:
462  ptp.num_param = 2;
465  break;
467  ptp.num_param = 1;
468  ptp.param1 = 0;
470  break;
472  ptp.num_param = 1;
473  ptp.param1 = 0;
476  break;
477  case PTP_CHDK_GetMemory:
478  {
479  char *src=(char *)param2;
480  int size=param3;
481  int result=0;
482  if ( size < 1 ) // invalid size? NULL is accepted
483  {
485  break;
486  }
487 
488  if (param4 == PTP_CHDK_GETMEM_MODE_DIRECT) {
489  int total_size = size;
490  // canon data->send_data fails on NULL, send first word separately
491  // DMA from addresses occupied by TCM is suspect but seems to work on many cams
492  // can't directly check NULL https://chdk.setepontos.com/index.php?topic=13101.0
493  if((unsigned)param2 < 4 ) {
494  char x[4];
495  int send_size = 4 - param2;
496  if(send_size > size) {
497  send_size = size;
498  }
499  memcpy(x,src,send_size);
500 
501  // 0 is success
502  if(data->send_data(data->handle,x,send_size,total_size,0,0,0) != 0) {
504  break;
505  }
506  // that was all, done
507  if(size == send_size) {
508  break;
509  }
510  size -= send_size;
511  // total only sent on first send
512  total_size = 0;
513  src+=send_size;
514  }
515  // no need to send through send_ptp, faster with one call
516  if(data->send_data(data->handle,src,size,total_size,0,0,0) == 0) {
517  result = 1;
518  }
519  } else if(param4 == PTP_CHDK_GETMEM_MODE_BUFFER) {
520  result = send_ptp_data_buffered(data,memcpy,src,size);
521  } // else error
522  if(!result)
523  {
525  }
526  break;
527  }
528  case PTP_CHDK_SetMemory:
529  if ( param2 == 0 || param3 < 1 ) // null pointer or invalid size?
530  {
532  break;
533  }
534 
535  data->get_data_size(data->handle); // XXX required call before receiving
536  if ( !recv_ptp_data(data,(char *) param2,param3) )
537  {
539  }
540  break;
541 
543  {
544  int s = data->get_data_size(data->handle);
545  if (s <= 0 || (s&3)) // no data or not an integer number of args
546  {
548  break;
549  }
550  unsigned *buf = malloc(s);
551 
552  if ( buf == NULL )
553  {
555  break;
556  }
557 
558  if ( recv_ptp_data(data,(char *) buf,s) )
559  {
560  ptp.num_param = 1;
561  ptp.param1 = call_func_ptr((void *)buf[0],(unsigned *)buf+1,(s-4)/4);
562  } else {
564  }
565 
566  free(buf);
567  break;
568  }
569 
570  case PTP_CHDK_TempData:
571  if ( param2 & PTP_CHDK_TD_DOWNLOAD )
572  {
573  const char *s = NULL;
574  size_t l = 0;
575 
576  if ( temp_data_kind == 0 )
577  {
579  break;
580  }
581 
582  if ( temp_data_kind == 1 )
583  {
584  s = temp_data.str;
585  l = temp_data_extra;
586  }
587 
588  if ( !send_ptp_data(data,s,l) )
589  {
591  break;
592  }
593 
594  } else if ( ! (param2 & PTP_CHDK_TD_CLEAR) ) {
595  if ( temp_data_kind == 1 )
596  {
597  free(temp_data.str);
598  }
599  temp_data_kind = 0;
600 
601  temp_data_extra = data->get_data_size(data->handle);
602 
603  temp_data.str = (char *) malloc(temp_data_extra);
604  if ( temp_data.str == NULL )
605  {
607  break;
608  }
609 
610  if ( !recv_ptp_data(data,temp_data.str,temp_data_extra) )
611  {
613  break;
614  }
615  temp_data_kind = 1;
616  }
617  if ( param2 & PTP_CHDK_TD_CLEAR )
618  {
619  if ( temp_data_kind == 1 )
620  {
621  free(temp_data.str);
622  }
623  temp_data_kind = 0;
624  }
625  break;
626 
627  case PTP_CHDK_UploadFile:
628  {
629  FILE *f=NULL;
630  char *fn=NULL;
631  unsigned data_size,fn_len;
633  data_size = data->get_data_size(data->handle);
634  // flush data would try to do init and fail again, so just break
635  if(!recv_ptp_data_init(&rs,data_size,NULL)) {
637  break;
638  }
639  int recv_err = 0;
640  while ( data_size > 0 ) {
641  if(!recv_ptp_data_chunk(&rs,data)) {
643  recv_err = 1; // flag PTP errors to avoid trying to read more in flush
644  break;
645  }
646  // first chunk, extact file name and write remaining data
647  if(!f) {
648  fn_len = *(unsigned *)rs.buf;
649  fn = malloc(fn_len+1);
650  if(!fn) {
652  break;
653  }
654  memcpy(fn,rs.buf+4,fn_len);
655  fn[fn_len] = 0;
656  f = fopen(fn,"wb");
657  free(fn);
658  if(!f) {
660  break;
661  }
662  fwrite(rs.buf+4+fn_len,1,rs.last_read - 4 - fn_len,f);
663  } else {
664  fwrite(rs.buf,1,rs.last_read,f);
665  }
666  data_size -= rs.last_read;
667  }
668 
669  if(f) {
670  fclose(f);
671  }
673  if(data_size > 0 && ptp.code != PTP_RC_OK && !recv_err) {
674  flush_recv_ptp_data(data,data_size);
675  }
676  break;
677  }
678 
680  {
681  FILE *f;
682  int tmp,t,total_size,r;
683  char *fn;
684 
685  if ( temp_data_kind != 1 )
686  {
687  // send dummy data, otherwise error hoses connection
688  send_ptp_data(data,"\0",1);
690  break;
691  }
692 
693  fn = (char *) malloc(temp_data_extra+1);
694  if ( fn == NULL )
695  {
696  // send dummy data, otherwise error hoses connection
697  send_ptp_data(data,"\0",1);
698  free(temp_data.str);
699  temp_data_kind = 0;
701  break;
702  }
703  memcpy(fn,temp_data.str,temp_data_extra);
704  fn[temp_data_extra] = '\0';
705 
706  free(temp_data.str);
707  temp_data_kind = 0;
708 
709  f = fopen(fn,"rb");
710  if ( f == NULL )
711  {
712  // send dummy data, otherwise error hoses connection
713  send_ptp_data(data,"\0",1);
715  free(fn);
716  break;
717  }
718  free(fn);
719 
720  fseek(f,0,SEEK_END);
721  total_size = ftell(f);
722  fseek(f,0,SEEK_SET);
723 
725  if(!send_ptp_data_buf_init(&sb,total_size))
726  {
727  // send dummy data, otherwise error hoses connection
728  send_ptp_data(data,"\0",1);
730  fclose(f);
731  break;
732  }
733 
734  tmp = total_size;
735  t = total_size;
736  while ( (r = fread(sb.buf,1,(t<sb.size)?t:sb.size,f)) > 0 )
737  {
738  t -= r;
739  data->send_data(data->handle,sb.buf,r,tmp,0,0,0);
740  tmp = 0;
741  }
742  fclose(f);
743  // XXX check that we actually read/send total_size bytes! (t == 0)
744 
745  ptp.num_param = 1;
746  ptp.param1 = total_size;
747 
749 
750  break;
751  }
752  break;
753 
755  {
756  int s;
757  char *buf;
758 
759  ptp.num_param = 2;
760  ptp.param1 = script_run_id; // in error case, ID of most recent script
761 
762  s = data->get_data_size(data->handle);
763 
764  if ( (param2&PTP_CHDK_SL_MASK) != PTP_CHDK_SL_LUA )
765  {
766  flush_recv_ptp_data(data,s);
768  break;
769  }
770 
771  buf = (char *) malloc(s);
772  if ( buf == NULL )
773  {
775  break;
776  }
777 
778  recv_ptp_data(data,buf,s);
779 
780  // applies to both running and "interrupted" state, since interrupted means running restore
782  // note script ID is still incremented in this case
783  if (param2 & PTP_CHDK_SCRIPT_FL_NOKILL) {
784  // no message is added in this case, since the running script might also be doing
785  // stuff with messages
787  free(buf);
788  break;
789  }
790  // kill the script
792  }
793  // empty message queues if requested.
794  if(param2 & PTP_CHDK_SCRIPT_FL_FLUSH_CAM_MSGS) {
796  }
797  // Script either was not running or has been killed, so safe to remove from inbound queue outside of kbd task
800  }
801 
802  // increment script ID if script is loaded
803  script_run_id++;
804  ptp.param1 = script_run_id;
805 
806  // error details will be passed in a message
807  if (script_start_ptp(buf) < 0) {
809  } else {
811  }
812 
813  free(buf);
814 
815  break;
816  }
818  {
819  char *pdata="";
820  unsigned datasize=1;
821 
823  ptp.num_param = 4;
824  if(msg) {
825  ptp.param1 = msg->type;
826  ptp.param2 = msg->subtype;
827  ptp.param3 = msg->script_id;
828  ptp.param4 = msg->size;
829  // empty messages must have a data phase, so use default if no data
830  if(msg->size) {
831  datasize = msg->size;
832  pdata = msg->data;
833  }
834  } else {
835  // return a fully formed message for easier handling
837  ptp.param2 = 0;
838  ptp.param3 = 0;
839  ptp.param4 = 0;
840  }
841 
842  // NOTE message is lost if sending failed
843  if ( !send_ptp_data(data,pdata,datasize) )
844  {
846  }
847  free(msg);
848  break;
849  }
851  {
852  int msg_size;
853  ptp_script_msg *msg;
854  ptp.num_param = 1;
856  if (!script_is_running()) {
858  } else if(param2 && (unsigned)param2 != script_run_id) {// check if target script for message is running
860  } else if(script_msg_q_full(&msg_q_in)) {
862  }
863 
864  msg_size = data->get_data_size(data->handle);
865 
866  // if something was wrong, don't bother creating message, just flush
867  if(ptp.param1 != PTP_CHDK_S_MSGSTATUS_OK) {
868  flush_recv_ptp_data(data,msg_size);
869  break;
870  }
872  if ( !msg ) // malloc error or zero size
873  {
874  // if size is zero, things will get hosed no matter what
875  flush_recv_ptp_data(data,msg_size);
877  break;
878  }
879  msg->script_id = param2;
880  if ( !recv_ptp_data(data,msg->data,msg->size) )
881  {
883  free(msg);
884  break;
885  }
886  if( !enqueue_script_msg(&msg_q_in,msg) ) {
888  free(msg);
889  }
890  break;
891  }
892 
894  {
895  extern int live_view_get_data(ptp_data *data, int flags);
896 
897  ptp.num_param = 1;
898  ptp.param1 = live_view_get_data(data,param2);
899  if(!ptp.param1)
900  {
902  // send dummy data, otherwise error hoses connection
903  send_ptp_data(data,"\0",1);
904  }
905  }
906  break;
908  ptp.num_param = 2;
909  remotecap_is_ready(&ptp.param1,&ptp.param2);
910  break;
912  {
913  unsigned int rcgd_size;
914  int rcgd_status;
915  char *rcgd_addr;
916  int rcgd_pos;
917 
918  rcgd_status = remotecap_get_data_chunk(param2, &rcgd_addr, &rcgd_size, &rcgd_pos);
919  ptp.num_param = 3;
920  ptp.param3 = rcgd_pos; //client needs to seek to this file position before writing the chunk (-1 = ignore)
921  if ( (rcgd_addr==0) || (rcgd_size==0) ) {
922  // send dummy data, otherwise error hoses connection
923  send_ptp_data(data,"\0",1);
924  ptp.param1 = 0; //size
925  ptp.param2 = 0; //0 = no more chunks
926  } else {
927  // send directly using send_data to avoid multiple send calls
928  data->send_data(data->handle,rcgd_addr,rcgd_size,rcgd_size,0,0,0);
929 
930  ptp.param1 = rcgd_size; //size
931  if(rcgd_status == REMOTECAP_CHUNK_STATUS_MORE) {
932  ptp.param2 = 1;
933  } else {
934  ptp.param2 = 0;
935  }
936  }
937  // data send complete, free hooks etc as needed, set error status if required
938  if(!remotecap_send_complete(rcgd_status,param2)) {
940  }
941  }
942  break;
943  default:
945  break;
946  }
947 
948  // send response
949  data->send_resp( data->handle, &ptp, 0 );
950 
951  return 1;
952 }
static void init_chdk_ptp ( )
static

Definiert in Zeile 29 der Datei ptp.c.

30 {
31  int r;
32 
33  // wait until ptp_handlers_info is initialised and add CHDK PTP interface
34  r = 0x17;
35  while ( r==0x17 )
36  {
38  msleep(250);
39  }
40 
41  ExitTask();
42 }
void init_chdk_ptp_task ( )

Definiert in Zeile 44 der Datei ptp.c.

45 {
46  CreateTask("InitCHDKPTP", 0x19, 0x200, init_chdk_ptp);
47 }
ptp_script_msg* ptp_script_create_msg ( unsigned  type,
unsigned  subtype,
unsigned  datasize,
const void *  data 
)

Definiert in Zeile 359 der Datei ptp.c.

359  {
360  ptp_script_msg *msg;
361  msg = malloc(sizeof(ptp_script_msg) + datasize);
362  msg->size = datasize;
363  msg->type = type;
364  msg->subtype = subtype;
365  // caller may fill in data themselves
366  // datasize may be empty (e.g. empty string)
367  if(data && datasize) {
368  memcpy(msg->data,data,msg->size);
369  }
370  return msg;
371 }
ptp_script_msg* ptp_script_read_msg ( void  )

Definiert in Zeile 380 der Datei ptp.c.

380  {
381  ptp_script_msg *msg;
382  while(1) {
383  msg = dequeue_script_msg(&msg_q_in);
384  // no messages
385  if(!msg) {
386  return NULL;
387  }
388  // does message belong to our script
389  if(!msg->script_id || msg->script_id == script_run_id) {
390  return msg;
391  } else {
392  // no: discard and keep looking
393  free(msg);
394  }
395  }
396 }
int ptp_script_write_error_msg ( unsigned  errtype,
const char *  err 
)

Definiert in Zeile 399 der Datei ptp.c.

399  {
401  return 0;
402  }
404  if(!msg) {
405  return 0;
406  }
407  return ptp_script_write_msg(msg);
408 }
int ptp_script_write_msg ( ptp_script_msg msg)

Definiert in Zeile 374 der Datei ptp.c.

374  {
375  msg->script_id = script_run_id;
376  return enqueue_script_msg(&msg_q_out,msg);
377 }
static int recv_ptp_data ( ptp_data data,
char *  buf,
int  size 
)
static

Definiert in Zeile 180 der Datei ptp.c.

181 {
183  if(!recv_ptp_data_init(&rs,size,buf)) {
184  return 0;
185  }
186  int status=1;
187  while(rs.total_read < size && status) {
188  status = recv_ptp_data_chunk(&rs,data);
189  }
191  return status;
192 }
static int recv_ptp_data_chunk ( recv_ptp_data_state_t rs,
ptp_data data 
)
static

Definiert in Zeile 117 der Datei ptp.c.

118 {
119  int size_left = rs->total_size - rs->total_read;
120  if(size_left <= 0) {
121  return 0;
122  }
123 #ifndef CAM_PTP_USE_NATIVE_BUFFER
124  // using unbuffered, has to be all in one go
125  if(!rs->buf) {
126  // TODO maybe shouldn't add to total on error?
127  rs->total_read = rs->last_read = rs->total_size;
128  if(data->recv_data(data->handle,rs->dst_buf,rs->total_size,0,0) != 0) {
129  return 0;
130  }
131  return 1;
132  }
133 #endif
134 
135  int rsize;
136  // less than one chunk remaining, read all
137  if(size_left <= rs->buf_size) {
138  rsize = size_left;
139  } else {
140  rsize = rs->buf_size;
141  // if on last full chunk, check for multi-read bug sizes
142  // https://chdk.setepontos.com/index.php?topic=4338.msg140577#msg140577
143  if(size_left <= rs->buf_size * 2) {
144  // assumes buf_size is multiple of 512, enforced in recv_ptp_data_init
145  int rest = size_left % rs->buf_size;
146  // if final transfer would be problem size, reduce size of next to last transfer by 1k
147  // if buffer size is less than 0x800, things are badly hosed anyway
148  if(rs->buf_size >= 0x800 && rest > 0x1f4 && rest < 0x3f4) {
149  rsize -= 0x400;
150  }
151  }
152  }
153  rs->last_read = rsize;
154  if(data->recv_data(data->handle,rs->buf,rsize,0,0) != 0) {
155  return 0;
156  }
157  if(rs->dst_buf) {
158  memcpy(rs->dst_buf + rs->total_read,rs->buf,rsize);
159  }
160  rs->total_read += rsize;
161  return 1;
162 }
static void recv_ptp_data_finish ( recv_ptp_data_state_t rs)
static

Definiert in Zeile 167 der Datei ptp.c.

168 {
169 #ifndef CAM_PTP_USE_NATIVE_BUFFER
170  free(rs->buf);
171 #endif
172  memset(rs,0,sizeof(recv_ptp_data_state_t));
173 }
static int recv_ptp_data_init ( recv_ptp_data_state_t rs,
int  total_size,
char *  dst_buf 
)
static

Definiert in Zeile 66 der Datei ptp.c.

67 {
68  memset(rs,0,sizeof(recv_ptp_data_state_t));
69 #ifdef CAM_PTP_USE_NATIVE_BUFFER
70  rs->buf_size = (get_ptp_file_buf_size() >> 1); // canon code seems to use half reported size for file buf
71  rs->buf = get_ptp_file_buf();
72 #else
73  //if using malloc, half of largest free block
74  rs->buf_size = (core_get_free_memory() >> 1);
75 #endif
76  // for testing smaller / fixed size chunks
77 #ifdef PTP_RECV_BUF_MAX_SIZE
78  if(rs->buf_size > PTP_RECV_BUF_MAX_SIZE) {
79  rs->buf_size = PTP_RECV_BUF_MAX_SIZE;
80  }
81 #endif
82  // clamp size is a multiple of 512 to simplify multi-read workaround (0x1f5 bug)
83  // https://chdk.setepontos.com/index.php?topic=4338.msg140577#msg140577
84  // size must also be multiple of 4 due to other issues on some cameras
85  // http://chdk.setepontos.com/index.php?topic=6730.msg76760#msg76760
86  rs->buf_size &= 0xFFFFFE00;
87  // things will be badly broken if only a few KB free, try to fail gracefully
88  if(rs->buf_size < 2048) {
89  return 0;
90  }
91  // requested size smaller that buffer
92  if(rs->buf_size > total_size) {
93  rs->buf_size = total_size;
94  }
95  rs->total_size = total_size;
96  rs->total_read = 0;
97  rs->last_read = 0;
98  rs->dst_buf = dst_buf;
99 
100 #ifndef CAM_PTP_USE_NATIVE_BUFFER
101  if(!dst_buf) {
102  rs->buf = malloc(rs->buf_size);
103  if(!rs->buf) {
104  return 0;
105  }
106  } else {
107  rs->buf = NULL;
108  }
109 #endif
110  return 1;
111 }
unsigned script_msg_q_empty ( ptp_script_msg_q q)

Definiert in Zeile 322 der Datei ptp.c.

322  {
323  return (q->w == q->r);
324 }
unsigned script_msg_q_full ( ptp_script_msg_q q)

Definiert in Zeile 318 der Datei ptp.c.

318  {
319  return (script_msg_q_next(q->w) == q->r);
320 }
unsigned script_msg_q_next ( unsigned  i)

Definiert in Zeile 311 der Datei ptp.c.

311  {
312  if(i == PTP_SCRIPT_MSG_Q_LEN - 1) {
313  return 0;
314  }
315  return i+1;
316 }
static long script_start_ptp ( char *  script)
static

Definiert in Zeile 432 der Datei ptp.c.

433 {
434  ptp_script = script;
435  while (ptp_script) msleep(10);
436  return ptp_script_state;
437 }
static int send_ptp_data ( ptp_data data,
const char *  src,
int  size 
)
static

Definiert in Zeile 239 der Datei ptp.c.

240 {
241  if ( data->send_data(data->handle,src,size,size,0,0,0) )
242  {
243  return 0;
244  }
245  return 1;
246 }
static void send_ptp_data_buf_free ( send_ptp_data_buf_t sb)
static

Definiert in Zeile 228 der Datei ptp.c.

229 {
230  free(sb->buf);
231  sb->buf=NULL;
232  sb->size=0;
233 }
static int send_ptp_data_buf_init ( send_ptp_data_buf_t sb,
int  total_size 
)
static

Definiert in Zeile 208 der Datei ptp.c.

209 {
210  int buf_size=(core_get_free_memory()>>1);
211  // make sure size is an integer number of words (avoid some possible issues with multiple calls)
212  buf_size &= 0xFFFFFFFC;
213  if(buf_size > total_size) {
214  buf_size = total_size;
215  }
216  sb->buf=malloc(buf_size);
217  if(!sb->buf) {
218  sb->size=0;
219  return 0;
220  }
221  sb->size=buf_size;
222  return 1;
223 }
static int send_ptp_data_buffered ( ptp_data data,
void *(*)(void *d, const void *s, long sz)  copy_fn,
const char *  src,
int  size 
)
static

Definiert in Zeile 253 der Datei ptp.c.

254 {
256  if(!send_ptp_data_buf_init(&sb,size)) {
257  return 0;
258  }
259 
260  int tmpsize = size;
261  int send_size;
262  while ( size > 0 )
263  {
264  if(size > sb.size) {
265  send_size = sb.size;
266  } else {
267  send_size = size;
268  }
269  // src inside buf ?
270  if(src >= sb.buf && src < sb.buf + send_size) {
271  // send whatever is in buffer without attempting to copy
272  if(src + size < sb.buf + sb.size) {
273  // all remainder is in buf
274  send_size = size;
275  } else {
276  // send up to end of buffer
277  send_size = sb.size - (src - sb.buf);
278  }
279  } else {
280  // full copy size would overlap
281  if(src < sb.buf && src + send_size > sb.buf) {
282  // copy up to start of buf
283  send_size = sb.buf - src;
284  }
285  copy_fn(sb.buf,src,send_size);
286  }
287  if ( data->send_data(data->handle,sb.buf,send_size,tmpsize,0,0,0) )
288  {
289  return 0;
290  }
291  tmpsize = 0;
292  size -= send_size;
293  src += send_size;
294  }
296  return 1;
297 }
void start_ptp_script ( )

Definiert in Zeile 415 der Datei ptp.c.

416 {
417  if (ptp_script)
418  {
419  module_set_script_lang(0); // Force Lua script language
421  {
424  }
425  else
426  ptp_script_state = -1;
427  ptp_script = 0;
428  }
429 }

Variablen-Dokumentation

ptp_script_msg_q msg_q_in

Definiert in Zeile 308 der Datei ptp.c.

ptp_script_msg_q msg_q_out

Definiert in Zeile 309 der Datei ptp.c.

char* ptp_script = 0
static

Definiert in Zeile 410 der Datei ptp.c.

int ptp_script_state = 0
static

Definiert in Zeile 411 der Datei ptp.c.

unsigned script_run_id
static

Definiert in Zeile 23 der Datei ptp.c.