#include <string>
#include <iostream>
#include <iomanip>
#include <sstream>
#include <cstdarg>
#include <cstdio>
#include <cstring>
#include <unistd.h>
#include "gpib-utils.h"
#include <DAQ++/Thread.h>
#if defined(HAS_GPIB)
int GPIB_debug = 0;
static bool GPIB_do_lock = true;
static DAQpp::Mutex GPIB_mutex;
#define usleep(x)
double TElapsed(time_t a)
{
time_t b;
time(&b);
//return ((double)(b-a)/(double)(CLOCKS_PER_SEC));
return (double)(b -a);
}
void GPIBdecodestatus()
{
int st = ibsta;
if ( st & ERR ) std::cout << "ERR " ;
if ( st & TIMO ) std::cout << "TIMO " ;
if ( st & END ) std::cout << "END " ;
if ( st & SRQI ) std::cout << "SRQI " ;
if ( st & RQS ) std::cout << "RQS " ;
if ( st & CMPL ) std::cout << "CMPL " ;
if ( st & LOK ) std::cout << "LOK " ;
if ( st & REM ) std::cout << "REM " ;
if ( st & CIC ) std::cout << "CIC " ;
if ( st & ATN ) std::cout << "ATN " ;
if ( st & TACS ) std::cout << "TACS " ;
if ( st & LACS ) std::cout << "LACS " ;
if ( st & DTAS ) std::cout << "DTAS " ;
if ( st & DCAS ) std::cout << "DCAS " ;
std::cout << std::endl;
}
const char* GPIBstatus()
{
static std::string the_line;
std::ostringstream os;
int st = ibsta;
if ( st & ERR ) os << "ERR " ;
if ( st & TIMO ) os << "TIMO " ;
if ( st & END ) os << "END " ;
if ( st & SRQI ) os << "SRQI " ;
if ( st & RQS ) os << "RQS " ;
if ( st & CMPL ) os << "CMPL " ;
if ( st & LOK ) os << "LOK " ;
if ( st & REM ) os << "REM " ;
if ( st & CIC ) os << "CIC " ;
if ( st & ATN ) os << "ATN " ;
if ( st & TACS ) os << "TACS " ;
if ( st & LACS ) os << "LACS " ;
if ( st & DTAS ) os << "DTAS " ;
if ( st & DCAS ) os << "DCAS " ;
the_line = os.str();
return the_line.c_str();
}
//////////////////////////////////////////////////////////////////////////
// GPIB
//
// Created: Sat May 08 23:09:59 1999 Author: Carlos
// Purpose: A few GPIB commands
//
//////////////////////////////////////////////////////////////////////////
std::string GPIBlastCommad;
bool GPIBRead(int dev, int delay, char *out, int sz)
{
if ( out == 0 )
return true ;
if (GPIB_do_lock)
GPIB_mutex.acquire();
ibrd(dev, out, sz);
if ( GPIB_debug )
{
std::cout << "* GPIB status ";
}
bool rc = (bool)(ibsta & ERR);
if ( !rc ) out[ibcntl] = 0;
else
{
sprintf(out, "GPIB error when reading: rc = %x", iberr);
GPIBdecodestatus();
}
if ( GPIB_debug && rc )
{
std::cout << "* GPIBRead: " << out << std::endl
<< "..." << std::flush;
GPIBdecodestatus();
}
if (GPIB_do_lock)
GPIB_mutex.release();
return rc;
}
bool GPIBWriteFast(int dev, const char *str)
{
GPIB_mutex.acquire();
ibwrt(dev, const_cast<char *>(str), strlen(str) + 1);
GPIB_mutex.release();
return (bool)( ibsta & ERR );
}
bool GPIBReadFast(int dev, char *out, int sz)
{
bool rc;
GPIB_mutex.acquire();
ibrd(dev, out, sz);
GPIB_mutex.release();
rc = (bool)(ibsta & ERR);
if ( !rc ) out[ibcntl] = 0;
return rc;
}
bool GPIBWrite(int dev, const char *fmt, ...)
{
std::ostringstream ocmmd;
const char *p;
va_list ap;
va_start(ap, fmt);
// Get the command
for (p = fmt;*p;p++)
{
if (*p != '%')
{
ocmmd << *p;
continue;
}
switch (*++p)
{
case 'x':
ocmmd << std::hex << va_arg(ap, int) << std::dec;
break;
case 'd':
case 'l':
case 'u':
case 'h':
ocmmd << va_arg(ap, int);
break;
case 'f':
ocmmd << va_arg(ap, double);
break;
case 's':
ocmmd << va_arg(ap, char *);
break;
default:
ocmmd << *p;
break;
}
}
GPIBlastCommad = ocmmd.str();
if ( GPIB_debug )
std::cout << "* GPIBWrite: " << GPIBlastCommad << std::endl;
GPIB_mutex.acquire();
ibwrt(dev, (void *)GPIBlastCommad.c_str(), GPIBlastCommad.size() + 1);
usleep(1);
if ( GPIB_debug )
{
std::cout << "* GPIB status ";
GPIBdecodestatus();
}
GPIB_mutex.release();
return (bool)( ibsta & ERR );
}
bool GPIBWriteRead(int dev, int delay, char *out, int sz, const char *fmt, ...)
{
std::ostringstream ocmmd;
const char *p;
va_list ap;
va_start(ap, fmt);
// Get the command
for (p = fmt;*p;p++)
{
if (*p != '%')
{
ocmmd << *p;
continue;
}
switch (*++p)
{
case 'x':
ocmmd << std::hex << va_arg(ap, int) << std::dec;
break;
case 'd':
case 'l':
case 'u':
case 'h':
ocmmd << va_arg(ap, int);
break;
case 'f':
ocmmd << va_arg(ap, double);
break;
case 's':
ocmmd << va_arg(ap, char *);
break;
default:
ocmmd << *p;
break;
}
}
GPIBlastCommad = ocmmd.str();
if ( GPIB_debug )
std::cout << "* GPIBWriteRead: " << GPIBlastCommad << std::endl;
GPIB_mutex.acquire();
GPIB_do_lock=false;
ibwrt(dev, (void *)GPIBlastCommad.c_str(), GPIBlastCommad.size() + 1);
usleep(1);
if ( GPIB_debug )
{
std::cout << "* GPIB status ";
GPIBdecodestatus();
}
bool rc = (bool)( ibsta & ERR );
if ( rc )
{
sprintf(out, "GPIB error when writing: rc = %d", iberr);
if ( GPIB_debug ) std::cout << "* " << out << std::endl;
return rc ;
}
bool rd = GPIBRead(dev, delay, out, sz);
GPIB_do_lock=true;
GPIB_mutex.release();
return rd;
}
#endif