Subversion Repositories shark

Rev

Rev 1428 | Rev 1444 | Go to most recent revision | Blame | Compare with Previous | Last modification | View Log | RSS feed

/*
 * Project: S.Ha.R.K.
 *
 * Coordinators:
 *   Giorgio Buttazzo    <giorgio@sssup.it>
 *   Paolo Gai           <pj@gandalf.sssup.it>
 *
 * Authors     :
 *   Giacomo Guidi       <giacomo@gandalf.sssup.it>
 *
 * ReTiS Lab (Scuola Superiore S.Anna - Pisa - Italy)
 *
 * http://www.sssup.it
 * http://retis.sssup.it
 * http://shark.sssup.it
 */


/*
 * Copyright (C) 2003 Giacomo Guidi
 *
 * 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., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 */


#include "kernel/kern.h"
#include "stdlib.h"
#include "unistd.h"

#include "drivers/shark_keyb26.h"
#include "drivers/shark_videodev26.h"
#include "drivers/shark_fb26.h"

#define WIDTH 640
#define HEIGHT 480
#define BYTES_PP 2

#define FG_PERIOD 40000
#define FG_WCET 30000
#define FG_W 320               
#define FG_H 200

void program_end(void *arg)
{

  sys_end();
 
}

void elaborate_image(void *imageptr);

TASK grab_task(void *arg) {

  struct video_picture vpic;
  struct video_buffer fbuf[2];
  struct video_window win;
  struct video_channel chan;
  int on,display,temp,save;

  task_nopreempt();

  /* Init videodev driver */
  VIDEODEV26_open(0);

  chan.channel = (int)(arg);
  chan.norm = VIDEO_TYPE_CAMERA;
                                                                                                                             
  VIDEODEV26_ioctl(0,VIDIOCSCHAN,(unsigned long)&chan);

  /* Select palette and depth */
  VIDEODEV26_ioctl(0,VIDIOCGPICT,(unsigned long)&vpic);
                                                                                                                             
  vpic.palette = VIDEO_PALETTE_GREY;
  vpic.depth = 8;                            
                                                                                                 
  VIDEODEV26_ioctl(0,VIDIOCSPICT,(unsigned long)&vpic);

  /* Double Buffering Strategy */

  fbuf[0].base = malloc(FG_W*FG_H);
  fbuf[0].height = FG_H;
  fbuf[0].width = FG_W;
  fbuf[0].bytesperline = FG_W;
  fbuf[0].depth = 8;
 
  fbuf[1].base = malloc(FG_W*FG_H);
  fbuf[1].height = FG_H;
  fbuf[1].width = FG_W;
  fbuf[1].bytesperline = FG_W;
  fbuf[1].depth = 8;

  VIDEODEV26_ioctl(0,VIDIOCSFBUF,(unsigned long)&(fbuf[0]));
  VIDEODEV26_ioctl(0,VIDIOCSFBUF,(unsigned long)&(fbuf[1]));

  /* Set grabbing window */
  VIDEODEV26_ioctl(0,VIDIOCGWIN,(unsigned long)&win);
                                                                                                                             
  win.x = 0;
  win.y = 0;
  win.width = FG_W;
  win.height = FG_H;
                                                                                                                             
  VIDEODEV26_ioctl(0,VIDIOCSWIN,(unsigned long)&win);

  task_preempt();
                               
  display = 1;
  save    = 0;
                                                                           
  while(1) {
                 
    task_nopreempt();
 
    /* Set the current buffer */
    VIDEODEV26_ioctl(0,VIDIOCSFBUF,(unsigned long)&(fbuf[save]));

    /* Start grabbing */
    on = 1;
    VIDEODEV26_ioctl(0,VIDIOCCAPTURE,(unsigned long)&on);
 
    task_preempt();
    /*
    printf_xy(1,20,WHITE,"%08x%08x",
        *(unsigned int *)(fbuf[display].base+50*320+50),
        *(unsigned int *)(fbuf[display].base+50*320+54));
    */

   
    elaborate_image(fbuf[display].base);

    /* Buffer switch */
    temp = display;
    display = save;
    save = temp;

    task_testcancel();
    task_endcycle();

  }

  return NULL;

}

extern void *video_memory;

void elaborate_image(void *imageptr)
{

  WORD x,y;
  BYTE *col;

    for(y = 0; y < FG_H; y++)
      for(x = 0; x < FG_W; x++) {

        col = (BYTE *)(imageptr + y * FG_W + x);
        *(WORD *)(video_memory + y*(WIDTH*2) + (x*2)) = (WORD)rgb16(*(BYTE *)(col),*(BYTE *)(col),*(BYTE *)(col));

    }

}

int main(int argc, char **argv)
{

  SOFT_TASK_MODEL st;
  PID grab_task_pid;

  if (argc < 2) return -1;

  soft_task_default_model(st);
  soft_task_def_period(st,40000);
  soft_task_def_met(st,30000);
  soft_task_def_arg(st, (void *)(atoi(argv[1])));
  soft_task_def_ctrl_jet(st);
 
  grab_task_pid = task_create("GrabTask",grab_task,&st,NULL);
  if (grab_task_pid == NIL) {
        cprintf("ERROR: Cannot create grab task\n");
        sys_end();
  }

  task_activate(grab_task_pid);

  while(keyb_getch(BLOCK) != ESC);

  task_kill(grab_task_pid);

  sleep(1);

  sys_end();

  return 0;

}