Getting Live Feed from Axis Camera in Windriver

So i have been trying to figure out how to connect to the axis camera through wireless. I can connect to the gaming adapter but not the camera. Im using windriver and found the default code for displaying images to the 10.xx.yy.6 ip-address but im unable to build it because of a missing header file PCVideoServer.h Im not sure if im just missing a program? an update? im not sure exactly any help would be greatly appreciated.

Thanks

Dave

This would be helpful for my team too.

As long as you have the latest update, you should have this file with the WPILib stuff so it would just be a matter of #include <PCVideoServer.h>. If that doesn’t work than I’m not sure how to fix that becuase as far as I can tell, we don’t actually have the individual header or .cpp files from the WPILib. I suppose one option would be to go download all the source files and then manually include the PCVideoServer.h (and PCVideoServer.cpp?) file in your project.

I know I’ve heard of people not being able to get the streaming images from the robot working (at least the Dashboard demo with the vision does not work for me :frowning: ) I’m not sure what that is being caused by so you may be doing something that will be fixed in the next update.

Our team was able to get the video server to work, but the problem is because the example code for it in windriver is broken… here are the steps to get it working (assuming that you’ve already applied the correct windriver and labview updates):

  1. first get the regular dashboard example in windriver to run on the cRio. (the one labeled “dashboardDataExample” - when this correctly loads on the cRio you should see all the lights on the dashboard flashing due to a counter in the code (what is on the dashboard doesn’t accurately represent what’s happening on the cRio automatically… you have to program it to respond correctly). The battery voltage and robot state should also be the same as is on the DS (anything displayed on the DS should display correctly on the dashboard at all times… this is not affected by the robot code).

  2. add the following code to the RobotMain() function in DashboardDataExample.cpp after right before the loop (but not inside it!):
    [INDENT]
    if (StartCameraTask(13, 0, k320x240, ROT_0) == -1) {
    [INDENT]//some error message
    }
    Wait(2.0);
    PCVideoServer pc;
    INT32 i;
    for (i = 0; i<60; i++) {
    Wait(1.0);
    }
    pc.Stop();
    for (i = 0; i<10; i++) {
    Wait(1.0);
    }
    pc.Start();
    [/INDENT][/INDENT]
    *I just copied this code from the camera server example in windriver because the code works, but that project does not compile correct code.

  3. make sure the following headers are declared in DashboardDataExample.cpp:

#include “vxWorks.h”
#include “AxisCamera.h”
#include “BaeUtilities.h”
#include “FrcError.h”
#include “PCVideoServer.h”

the code should now compile are run the video server for you to see on the dashboard.

  • if you don’t know how to find the dashboard executable, just open Labview, open the dashboard project and either run it or build it into an executable (you’ll also have to make sure that your computer is manually configured to the ip address 10.xx.yy.6

*note: with this example, you might run into the compile error that i is declared twice… just remove the INT32 from the second declaration (which should set i to zero right before the main loop).

I’m not too impressed by the documentation FIRST gave us for the camera/video server/dashboard. This all took some searching to figure out.

I was just playing around and I dont think you need to stop then start it again (and wait the 60 seconds…)

so just this works:


PCVideoServer pc;

We are able to get a live feed from the camera using:


PCVideoServer *pc = new PCVideoServer();

but not any other method mentioned above.

However,

Every time after the first time we run or debug after a cRIO restart, we get a Bind: EADDRINUSE error.

Is anyone else having this problem?

If we restart the cRIO, it works once afterwards, then we get the error on subsequent debug/run attempts.

I was getting the EADDRINUSE thing when I was declaring PCVideoServer as a pointer and making it on the heap. That error stopped when I just declared it on the stack

PCVideoServer pc;

however I have no idea what that error means :frowning:

That may be the case… I haven’t played around with it enough myself. The code I posted was simply copied from the video server example in windriver.

it may be that this code stops the camera first and includes the delays in order to prevent some of the errors that other people are having.

EADDRINUSE is a POSIX error type that is returned when you try to bind an IP socket to a port/address combination that is already in use. For example, if you try to run two web servers on port 80 on your server, only the first instance will be able to bind a socket to port 80, and the other will return as an error with errno EADDRINUSE.

What’s happening in your case is that when you declare PCVideoServer on the heap (with new), you bind the video server port on the cRIO, but you never actually delete the PCVideoServer object before your user program completes. Only when the destructor method of PCVideoServer is called is the port actually released:


void server_heap_bad()
{
   PCVideoServer *server = new PCVideoServer();
   // when this function returns, you lose the pointer to the PCVideoServer object.
   // The PCVideoServer object remains allocated and active, but you can no
   // longer deallocate it because you don't know where it is (this is called a
   // "dangling pointer" error).
   // Thus the video port remains bound until you reboot the cRIO.
}

void server_heap_good()
{
   PCVideoServer *server = new PCVideoServer();
   
   //... do stuff
   delete server; // calls PCVideoServer::~PCVideoServer, which unbinds the port.
}

void server_stack_good()
{
   PCVideoServer server;

   // when this function returns, the server instance is automatically destroyed
   // without the need for **delete**.  Thus the port will be unbound.
}

Hope this makes sense; in most modern operating systems, the operating system would perform garbage collection on all open handles, including sockets, and eventually the port would automatically be unbound - but this behavior cannot be relied on and may not happen when you kill your project in Wind River.