Wojtek Lerch wrote:
PtInit() simply returns a -1. The documentation does not explain how to
get any further diagnostics out of the function.
Still, there’s a good chance that errno may give us a hint.
errno does not appear to be set by PtInit: EOK
Is PtInit() one of the first things you call in your program?
It is now. I moved it up so that it’s the absolute first thing called
when the program starts. Okay, PtInit now seems to work, but when I call
for it to grab the screen, it doesn’t grab anything.
Could you make a copy of ped or pterm, make it setuid root, and see if
it works on your system?
Yes, and both work properly.
I also tried doing the same thing to snapshot. It works like a charm!
Frustrating…
Here’s the code that demonstrates the problem. As a normal user, it
works. But if I make the program SUID root (chmod 4755) it doesn’t work:
//qcc grabscreen.c -o grabscreen -lph -lphexlib
#include <iostream.h>
#include <stdio.h>
#include <Pt.h>
// make sure we include BMP support!
#define PX_IMAGE_MODULES
#define PX_PHIMAGE_SUPPORT
#define PX_BMP_SUPPORT
#include <photon/PxImage.h>
int print(PhImage_t *image)
{
int iErrCode = 0;
PhDrawContext_t pdc = 0;
PpPrintContext_t mpPC;
PhPoint_t p = { 0, 0 };
mpPC = PpCreatePC();
if (mpPC)
{
// set up my context
if(!iErrCode)
{
PpSetPC(mpPC, Pp_PC_DRIVER, “/usr/bin/phs-to-ps”, 0);
PpSetPC(mpPC, Pp_PC_FILENAME, “grabscreen.phs”, 0);
Ph_rect xPrintArea;
xPrintArea.ul.x = 750;
xPrintArea.ul.y = 500;
xPrintArea.lr.x = 500;
xPrintArea.lr.y = 400;
PpSetPC(mpPC, Pp_PC_MARGINS, &xPrintArea, 0);
PhDim_t xPaperSize;
xPaperSize.w = 8500;
xPaperSize.h = 11000;
PpSetPC(mpPC, Pp_PC_PAPER_SIZE, &xPaperSize, 0);
PhDim_t xSourceSize;
xSourceSize.w = 1024;
xSourceSize.h = 768;
PpSetPC(mpPC, Pp_PC_SOURCE_SIZE, &xSourceSize, 0);
}
// initialize the print job
if(!iErrCode)
{
if(PpStartJob(mpPC))
iErrCode = 2;
}
// make the print context active
if(!iErrCode)
{
pdc = PpContinueJob(mpPC);
if(!pdc)
iErrCode = 3;
}
if (image == NULL)
{
cout << “ERROR: NULL image” << endl;
exit(1);
}
cout << "image size: " << image->size.w << “x” << image->size.h << endl;
PgSetPalette( image->palette, 0, 0, image->colors,
Pg_PALSET_SOFT, 0 );
iErrCode = PgDrawImage( image->image, image->type, &p,
&image->size, image->bpl, 0 );
cout << "iErrCode = " << iErrCode << endl;
PpEndJob(mpPC);
PpReleasePC(mpPC);
}
}
int snap(char *fname,PhRect_t rect)
{
int len;
char *mem;
PhImage_t *image;
// get the size of the shared memory you need for the image
if ((len=PgReadScreenSize(&rect))<=0) return -1;
// allocate shared memory to contain the image
if (!(mem=(char*)PgShmemCreate(len,NULL))) return -1;
// read the portion of the screen you’re interested in
if (image=PgReadScreen(&rect,mem))
{
// save the image to the file name given
PxWriteImage(fname,image,NULL,PX_IMAGE_BMP,0);
if ((image = PxLoadImage( fname, NULL )) == NULL) {
perror( “Unable to load image” );
return -1;
}
print(image);
}
// destroy the shared memory you used
PgShmemDestroy(mem);
return 0;
}
int main(int argc,char *argv[])
{
int i;
if (argc!=2)
{
printf("Usage: grab ");
exit(-1);
}
int iPtInit = PtInit("/dev/photon");
cout << "PtInit returned: " << iPtInit << endl;
// get a connection to Photon
if (iPtInit!=0)
{
perror(“Error: Could not connect to Photon.”);
exit(-1);
}
PhRect_t rect;
char fname[120];
//windows_rect(r,&rect);
rect.ul.x = 0;
rect.ul.y = 0;
rect.lr.x = 1023;
rect.lr.y = 767;
sprintf(fname,argv[1],i);
printf(“saving ‘%s’\n”,fname);
snap(fname,rect);
return 0;
}