/* Copyright 2007, 2008, 2009 Free Software Foundation, Inc.

   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 3 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, see <http://www.gnu.org/licenses/>.

   This file is part of the gdb testsuite.

   Contributed by Markus Deuling <deuling@de.ibm.com>.
   Tests for 'info spu' commands.  */

#include <stdio.h>
#include <string.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <spu_mfcio.h>


/* PPE-assisted call interface.  */
void
send_to_ppe (unsigned int signalcode, unsigned int opcode, void *data)
{
  __vector unsigned int stopfunc =
    {
      signalcode,     /* stop */
      (opcode << 24) | (unsigned int) data,
      0x4020007f,     /* nop */
      0x35000000      /* bi $0 */
    };

  void (*f) (void) = (void *) &stopfunc;
  asm ("sync");
  f ();
}

/* PPE-assisted call to mmap from SPU.  */
unsigned long long
mmap_ea (unsigned long long start, size_t length,
         int prot, int flags, int fd, off_t offset)
{
  struct mmap_args
    {
      unsigned long long start __attribute__ ((aligned (16)));
      size_t length __attribute__ ((aligned (16)));
      int prot __attribute__ ((aligned (16)));
      int flags __attribute__ ((aligned (16)));
      int fd __attribute__ ((aligned (16)));
      off_t offset __attribute__ ((aligned (16)));
    } args;

  args.start = start;
  args.length = length;
  args.prot = prot;
  args.flags = flags;
  args.fd = fd;
  args.offset = offset;

  send_to_ppe (0x2101, 11, &args);
  return args.start;
}

/* This works only in a Linux environment with <= 1024 open
   file descriptors for one process. Result is the file
   descriptor for the current context if available.  */
int
find_context_fd (void)
{
  int dir_fd = -1;
  int i;

  for (i = 0; i < 1024; i++)
    {
      struct stat stat;

      if (fstat (i, &stat) < 0)
        break;
      if (S_ISDIR (stat.st_mode))
        dir_fd = dir_fd == -1 ? i : -2;
    }
  return dir_fd < 0 ? -1 : dir_fd;
}

/* Open the context file and return the file handler.  */
int
open_context_file (int context_fd, char *name, int flags)
{
  char buf[128];

  if (context_fd < 0)
    return -1;

  sprintf (buf, "/proc/self/fd/%d/%s", context_fd, name);
  return open (buf, flags);
}


int
do_event_test ()
{
  spu_write_event_mask (MFC_MULTI_SRC_SYNC_EVENT); /* 0x1000 */  /* Marker Event */
  spu_write_event_mask (MFC_PRIV_ATTN_EVENT); /* 0x0800 */
  spu_write_event_mask (MFC_LLR_LOST_EVENT); /* 0x0400 */
  spu_write_event_mask (MFC_SIGNAL_NOTIFY_1_EVENT); /* 0x0200 */
  spu_write_event_mask (MFC_SIGNAL_NOTIFY_2_EVENT); /* 0x0100 */
  spu_write_event_mask (MFC_OUT_MBOX_AVAILABLE_EVENT); /* 0x0080 */
  spu_write_event_mask (MFC_OUT_INTR_MBOX_AVAILABLE_EVENT); /* 0x0040 */
  spu_write_event_mask (MFC_DECREMENTER_EVENT); /* 0x0020 */
  spu_write_event_mask (MFC_IN_MBOX_AVAILABLE_EVENT); /* 0x0010 */
  spu_write_event_mask (MFC_COMMAND_QUEUE_AVAILABLE_EVENT); /* 0x0008 */
  spu_write_event_mask (MFC_LIST_STALL_NOTIFY_EVENT); /* 0x0002 */
  spu_write_event_mask (MFC_TAG_STATUS_UPDATE_EVENT); /* 0x0001 */

  return 0;
}

int
do_dma_test ()
{
  #define MAP_FAILED      (-1ULL)
  #define PROT_READ       0x1
  #define MAP_PRIVATE     0x002
  #define BSIZE 128
  static char buf[BSIZE] __attribute__ ((aligned (128)));
  char *file = "/var/tmp/tmp_buf";
  struct stat fdstat;
  int fd, cnt;
  unsigned long long src;

  /* Create a file and fill it with some bytes.  */
  fd = open (file, O_CREAT | O_RDWR | O_TRUNC, 0777);
  if (fd == -1)
    return -1;
  memset ((void *)buf, '1', BSIZE);
  write (fd, buf, BSIZE);
  write (fd, buf, BSIZE);
  memset ((void *)buf, 0, BSIZE);

  if (fstat (fd, &fdstat) != 0
      || !fdstat.st_size)
    return -2;

  src = mmap_ea(0ULL, fdstat.st_size, PROT_READ, MAP_PRIVATE, fd, 0);
  if (src == MAP_FAILED)
    return -3;

  /* Copy some data via DMA.  */
  mfc_get (&buf, src, BSIZE, 5, 0, 0);   /* Marker DMA */
  mfc_write_tag_mask (1<<5);   /* Marker DMAWait */
  spu_mfcstat (MFC_TAG_UPDATE_ALL);

  /* Close the file.  */
  close (fd);

  return cnt;
}

int
do_mailbox_test ()
{
  /* Write to SPU Outbound Mailbox.  */
  if (spu_stat_out_mbox ())            /* Marker Mbox */
    spu_write_out_mbox (0x12345678);

  /* Write to SPU Outbound Interrupt Mailbox.  */
  if (spu_stat_out_intr_mbox ())
    spu_write_out_intr_mbox (0x12345678);

  return 0;       /* Marker MboxEnd */
}

int
do_signal_test ()
{
  struct stat fdstat;
  int context_fd = find_context_fd ();
  int ret, buf, fd;

  buf = 23;    /* Marker Signal */
  /* Write to signal1.  */
  fd = open_context_file (context_fd, "signal1", O_RDWR);
  if (fstat (fd, &fdstat) != 0)
    return -1;
  ret = write (fd, buf, sizeof (int));
  close (fd);  /* Marker Signal1 */

  /* Write to signal2.  */
  fd = open_context_file (context_fd, "signal2", O_RDWR);
  if (fstat (fd, &fdstat) != 0)
    return -1;
  ret = write (fd, buf, sizeof (int));
  close (fd);  /* Marker Signal2 */

  /* Read signal1.  */
  if (spu_stat_signal1 ())
    ret = spu_read_signal1 ();

  /* Read signal2.  */
  if (spu_stat_signal2 ())
    ret = spu_read_signal2 ();   /* Marker SignalRead */

  return 0;
}

int
main (unsigned long long speid, unsigned long long argp, 
      unsigned long long envp)
{
  int res;

  /* info spu event  */
  res = do_event_test ();

  /* info spu dma  */
  res = do_dma_test ();

  /* info spu mailbox  */
  res = do_mailbox_test ();

  /* info spu signal  */
  res = do_signal_test ();

  return 0;
}

