Beispiel #1
0
static int
delete_file_func (CameraFilesystem *fs, const char *folder,
		  const char *filename, void *data, GPContext *context)
{
	Camera *camera = data;
	int idx;

	idx = get_file_idx(camera, folder, filename);
	if (idx < 0)
		return idx;

	CHECK (tp6801_delete_file(camera, idx))

	return tp6801_commit(camera);
}
Beispiel #2
0
static int
delete_file_func (CameraFilesystem *fs, const char *folder,
		  const char *filename, void *data, GPContext *context)
{
	Camera *camera = data;
	int ret, idx;

	idx = get_file_idx(camera->pl, folder, filename);
	if (idx < 0)
		return idx;

	ret = st2205_delete_file(camera, idx);
	if (ret < 0) return ret;

	/* Also remove the file from our cached filelist */
	camera->pl->filenames[idx][0] = 0;

	return st2205_commit(camera);
}
Beispiel #3
0
static int
get_file_func (CameraFilesystem *fs, const char *folder, const char *filename,
	       CameraFileType type, CameraFile *file, void *data,
	       GPContext *context)
{
	Camera *camera = data;
	int idx, size;
#ifdef HAVE_GD
	int ret;
	gdImagePtr im, rotated;
	void *gdpng;
#endif

	idx = get_file_idx(camera->pl, folder, filename);
	if (idx < 0)
		return idx;

	if (type == GP_FILE_TYPE_RAW) {
		unsigned char *raw;

		size = st2205_read_raw_file (camera, idx, &raw);
		if (size < 0) return size;

		gp_file_set_mime_type (file, GP_MIME_RAW);
		gp_file_set_name (file, filename);
		gp_file_set_data_and_size (file, (char *)raw, size);

		return GP_OK;
	}

#ifdef HAVE_GD
	if (type != GP_FILE_TYPE_NORMAL)
		return GP_ERROR_NOT_SUPPORTED;

	im = gdImageCreateTrueColor(camera->pl->width, camera->pl->height);
	if (im == NULL)
		return GP_ERROR_NO_MEMORY;

	ret = st2205_read_file(camera, idx, im->tpixels);
	if (ret < 0) {
		gdImageDestroy (im);
		return ret;
	}

	if (needs_rotation (camera)) {
		rotated = gdImageCreateTrueColor (im->sy, im->sx);
		if (rotated == NULL) {
			gdImageDestroy (im);
			return GP_ERROR_NO_MEMORY;
		}
		rotate270 (im, rotated);
		gdImageDestroy (im);
		im = rotated;
	}

	gdpng = gdImagePngPtr(im, &size);
	gdImageDestroy (im);
	if (gdpng == NULL)
		return GP_ERROR_NO_MEMORY;

	ret = gp_file_set_mime_type (file, GP_MIME_PNG);
	if (ret < 0) { gdFree (gdpng); return ret; }

	ret = gp_file_set_name (file, filename); 
	if (ret < 0) { gdFree (gdpng); return ret; }

	ret = gp_file_append (file, gdpng, size);
	gdFree (gdpng);
	return ret;
#else
	gp_log(GP_LOG_ERROR,"st2205", "GD decompression not supported - no libGD present during build");
	return GP_ERROR_NOT_SUPPORTED;
#endif
}
  // TODO: read/write external should use buffer->valid_db_size instead of passing in additional
  // parameters
  void *DiskIOThread::run_thread(void *_thr_info){
    DiskIOThread *diskio = (DiskIOThread *) _thr_info;

    int ret = zmq_socket_monitor(diskio->sock, "inproc://monitor.router_sock", ZMQ_EVENT_CONNECTED | ZMQ_EVENT_ACCEPTED | ZMQ_EVENT_DISCONNECTED);
    if(ret < 0){
      diskio->status = -1;
      return NULL;
    }

    zmq::socket_t monitor_sock(*diskio->zmq_ctx, ZMQ_PAIR);
    try{
      monitor_sock.connect("inproc://monitor.router_sock");
    }catch(zmq::error_t &e){
      std::cout << "monitor socket create failed" << std::endl;
      return NULL;
    }

    zmq::pollitem_t pollitems[3];
    pollitems[0].socket = diskio->sock;
    pollitems[0].events = ZMQ_POLLIN;
    pollitems[1].socket = monitor_sock;
    pollitems[1].events = ZMQ_POLLIN;
    pollitems[2].socket = diskio->cancel_sock;
    pollitems[2].events = ZMQ_POLLIN;

    while(true){
      try {
        zmq::poll(pollitems, 3);
      }catch(...){
        std::cout << "error from poll!" << std::endl;
        return NULL;
      }

      if(pollitems[2].revents){
        int32_t cid;
        boost::shared_array<uint8_t> data;
        int32_t len = recv_msg(diskio->cancel_sock, cid, data);
        if(len < 0){
          diskio->status = -1;
          return NULL;
        }

        EMsgType type = *((EMsgType *) data.get());
        int32_t extern_cid, sock_idx;

        switch(type){
        case DiskIOCancel:
          extern_cid = zmq_rid_to_cid(cid);
          sock_idx = cid_to_sock_idx(extern_cid);
          diskio->client_valid[sock_idx] = false;
          break;
        case DiskIOEnable:
          extern_cid = zmq_rid_to_cid(cid);
          sock_idx = cid_to_sock_idx(extern_cid);
          diskio->client_valid[sock_idx] = true;
          break;
        default:
          assert(0);
          diskio->status = -1;
          return NULL;
        }
        continue;
      }

      if(pollitems[0].revents){
        int32_t cid;
        boost::shared_array<uint8_t> data;
        int32_t len = recv_msg(diskio->sock, cid, data);
        if(len < 0){
          assert(0);
          diskio->status = -1;
          return NULL;
        }
        //std::cout << "received from cid = " << std::hex << cid << std::dec << std::endl;
        EMsgType type = *((EMsgType *) data.get());
        Buffer *buf;
        std::string base; // for DiskIOExternal, base is actually fullpath
        int32_t extern_cid;
        int32_t sock_idx;
        if(type == DiskIORead || type == DiskIOWrite || type == DiskIOReadExternal
            || type == DiskIOWriteExternal || type == DiskIOWriteRead){
          len = recv_msg(diskio->sock, data);
          if(len < 0){
            assert(0);
            diskio->status = -1;
            return NULL;
          }
          buf = *((Buffer **) data.get());
          len = recv_msg(diskio->sock, data);
          if(len < 0){
            assert(0);
            diskio->status = -1;
            return NULL;
          }
          base = std::string((char *) data.get());
        }

        //std::cout << "request type = " << type << std::endl;

        block_id_t bid;
        int32_t extern_size;
        int32_t dbsize;
        int64_t offset;
        int32_t fidx;
        int32_t suc;
        std::string fname;
        int32_t rsize;
        int32_t wsuc;
        int32_t rd_db_id;
        EMsgType re_type;
        switch(type){
        case DiskIORead:
          bid = buf->get_block_id();

          dbsize = buf->get_db_size();
          fidx = get_file_idx(bid, dbsize, offset);
          fname = build_filename(diskio->datapath, base, fidx);

          extern_cid = zmq_rid_to_cid(cid);
          sock_idx = cid_to_sock_idx(extern_cid);
          if(!diskio->client_valid[sock_idx]){
            rsize = 0;
            re_type = DiskIOReadNotDone;
          }else{
            // read data from specified file, with
            rsize = dir_read(buf->get_db_ptr(), dbsize, fname.c_str(), offset);
            re_type = DiskIOReadDone;
          }

          // finished reading send back message
          suc = send_msg(diskio->sock, cid, (uint8_t *) &re_type, sizeof(Buffer *), ZMQ_SNDMORE);
          if(suc < 0){
            assert(0);
            diskio->status = -1;
            return NULL;
          }
          send_msg(diskio->sock, (uint8_t *) &buf, sizeof(Buffer *), ZMQ_SNDMORE);
          if(suc < 0){
            assert(0);
            diskio->status = -1;
            return NULL;
          }
          suc = send_msg(diskio->sock, (uint8_t *) &rsize, sizeof(int32_t), 0);
          if(suc < 0){
            assert(0);
            diskio->status = -1;
            return NULL;
          }
          break;

        case DiskIOWrite:

          bid = buf->get_block_id();

          dbsize = buf->get_db_size();
          fidx = get_file_idx(bid, dbsize, offset);
          fname = build_filename(diskio->datapath, base, fidx);
          // read data from specified file, with
          wsuc = dir_write(buf->get_db_ptr(), dbsize, fname.c_str(), offset);
          re_type = DiskIOWriteDone;

          // finished reading send back message
          suc = send_msg(diskio->sock, cid, (uint8_t *) &re_type, sizeof(Buffer *), ZMQ_SNDMORE);
          if(suc < 0){
            assert(0);
            diskio->status = -1;
            return NULL;
          }
          send_msg(diskio->sock, (uint8_t *) &buf, sizeof(Buffer *), ZMQ_SNDMORE);
          if(suc < 0){
            assert(0);
            diskio->status = -1;
            return NULL;
          }
          suc = send_msg(diskio->sock, (uint8_t *) &wsuc, sizeof(int32_t), 0);
          if(suc < 0){
            assert(0);
            diskio->status = -1;
            return NULL;
          }
          break;
        case DiskIOWriteRead:
          len = recv_msg(diskio->sock, data);
          if(len < 0){
            assert(0);
            diskio->status = -1;
            return NULL;
          }
          rd_db_id = *((int32_t *) data.get());

          bid = buf->get_block_id();
          dbsize = buf->get_db_size();
          fidx = get_file_idx(bid, dbsize, offset);
          fname = build_filename(diskio->datapath, base, fidx);

          // write data to
          wsuc = dir_write(buf->get_db_ptr(), dbsize, fname.c_str(), offset);

          int32_t resp_val;

          extern_cid = zmq_rid_to_cid(cid);
          sock_idx = cid_to_sock_idx(extern_cid);
          if(!diskio->client_valid[sock_idx]){
            resp_val = 0;
            re_type = DiskIOWriteReadWriteDone;
          }else{
            if(wsuc == 0){
              fidx = get_file_idx(rd_db_id, dbsize, offset);
              fname = build_filename(diskio->datapath, base, fidx);
              rsize = dir_read(buf->get_db_ptr(), dbsize, fname.c_str(), offset);
            }
            if(wsuc < 0 || rsize < 0){
              resp_val = -1;
            }else{
              resp_val = rsize;
            }
            re_type = DiskIOWriteReadDone;
          }
          // finished reading send back message
          suc = send_msg(diskio->sock, cid, (uint8_t *) &re_type, sizeof(Buffer *), ZMQ_SNDMORE);
          if(suc < 0){
            assert(0);
            diskio->status = -1;
            return NULL;
          }
          send_msg(diskio->sock, (uint8_t *) &buf, sizeof(Buffer *), ZMQ_SNDMORE);
          if(suc < 0){
            diskio->status = -1;
            return NULL;
          }
          suc = send_msg(diskio->sock, (uint8_t *) &resp_val, sizeof(int32_t), 0);
          if(suc < 0){
            diskio->status = -1;
            return NULL;
          }
          break;
        case DiskIOReadExternal:

          len = recv_msg(diskio->sock, data);
          if(len < 0){
            assert(0);
            diskio->status = -1;
            return NULL;
          }
          offset = *((int64_t *) data.get());

          len = recv_msg(diskio->sock, data);
          if(len < 0){
            assert(0);
            diskio->status = -1;
            return NULL;
          }
          extern_size = *((int32_t *) data.get());
          //std::cout << "size to read = " << extern_size << std::endl;

          extern_cid = zmq_rid_to_cid(cid);
          sock_idx = cid_to_sock_idx(extern_cid);
          if(!diskio->client_valid[sock_idx]){
            rsize = 0;
            re_type = DiskIOReadExternalNotDone;
          }else{
            //std::cout << "received request to read external data" << std::endl;
            dbsize = buf->get_db_size();
            if(extern_size > dbsize){
              assert(0);
              diskio->status = -1;
              return NULL;
            }
            fname = std::string(base);
            // read data from specified file, with
            rsize = dir_read(buf->get_db_ptr(), extern_size, fname.c_str(), offset);
            re_type = DiskIOReadExternalDone;
          }
          buf->set_valid_db_size(rsize);

          // finished reading send back message
          suc = send_msg(diskio->sock, cid, (uint8_t *) &re_type, sizeof(EMsgType),
                         ZMQ_SNDMORE);
          if(suc < 0){
            assert(0);
            diskio->status = -1;
            return NULL;
          }

          send_msg(diskio->sock, (uint8_t *) &buf, sizeof(Buffer *), ZMQ_SNDMORE);
          if(suc < 0){
            assert(0);
            diskio->status = -1;
            return NULL;
          }

          suc = send_msg(diskio->sock, (uint8_t *) &rsize, sizeof(int32_t), 0);
          if(suc < 0){
            assert(0);
            diskio->status = -1;
            return NULL;
          }
          break;

        case DiskIOWriteExternal:
          len = recv_msg(diskio->sock, data);
          if(len < 0){
            assert(0);
            diskio->status = -1;
            return NULL;
          }
          offset = *((int64_t *) data.get());

          len = recv_msg(diskio->sock, data);
          if(len < 0){
            assert(0);
            diskio->status = -1;
            return NULL;
          }

          // if has been canceled, don't send response
          extern_cid = zmq_rid_to_cid(cid);
          sock_idx = cid_to_sock_idx(extern_cid);
          if(diskio->client_sock[sock_idx] == NULL) continue;

          extern_size = *((int32_t *) data.get());

          dbsize = buf->get_db_size();
          //std::cout << "extern_size = " << extern_size << " dbsize = " << dbsize << std::endl;
          assert(extern_size <= dbsize);

          fname = std::string(base);

          // read data from specified file, with
          rsize = reg_write(buf->get_db_ptr(), extern_size, fname.c_str(), offset);
          re_type = DiskIOWriteExternalDone;

          // finished reading send back message
          suc = send_msg(diskio->sock, cid, (uint8_t *) &re_type, sizeof(Buffer *),
              ZMQ_SNDMORE);
          if(suc < 0){
            assert(0);
            diskio->status = -1;
            return NULL;
          }
          send_msg(diskio->sock, (uint8_t *) &buf, sizeof(Buffer *), ZMQ_SNDMORE);
          if(suc < 0){
            assert(0);
            diskio->status = -1;
            return NULL;
          }
          suc = send_msg(diskio->sock, (uint8_t *) &rsize, sizeof(int32_t), 0);
          if(suc < 0){
            assert(0);
            diskio->status = -1;
            return NULL;
          }
          break;
        case DiskIOShutDown:
          std::cout << "diskio thread received shutdown message" << std::endl;
          return NULL;
          break;
        case DiskIOConn:
          break;
        default:
          std::cout << "!!!!!!!!!diskio thread msgtype = " << type << std::endl;
          assert(0);
          diskio->status = -1;
          return NULL;
        }
        continue;
      }

      if(pollitems[1].revents){
        zmq_event_t *event;
        boost::shared_array<uint8_t> data;
        int len;
        len = recv_msg(monitor_sock, data);

        if (len < 0){
          assert(0);
          diskio->status = -11;
          return NULL;
        }
        assert(len == sizeof(zmq_event_t));
        event = (zmq_event_t *) data.get();

        switch (event->event){
        case ZMQ_EVENT_CONNECTED:
          std::cout << "established connection." << std::endl;
          break;
        case ZMQ_EVENT_ACCEPTED:
          std::cout << "connection accepted" << std::endl;
          break;
        case ZMQ_EVENT_DISCONNECTED:
          std::cout << "client disconnected" << std::endl;
          break;
        default:
          std::cout << "unexpected event" << std::endl;
          return NULL;
        }
        continue;
      }
    }
    return NULL;
  }