Deleted Added
sdiff udiff text old ( 8871:136328e218f2 ) new ( 9330:4a3269a11230 )
full compact
1/*
2 * Copyright (c) 2010 ARM Limited
3 * All rights reserved
4 *
5 * The license below extends only to copyright in the software and shall
6 * not be construed as granting a license to any other intellectual
7 * property including but not limited to intellectual property relating
8 * to a hardware implementation of the functionality of the software

--- 52 unchanged lines hidden (view full) ---

61#include "base/socket.hh"
62#include "base/trace.hh"
63#include "debug/VNC.hh"
64#include "sim/byteswap.hh"
65#include "sim/core.hh"
66
67using namespace std;
68
69/**
70 * Poll event for the listen socket
71 */
72VncServer::ListenEvent::ListenEvent(VncServer *vs, int fd, int e)
73 : PollEvent(fd, e), vncserver(vs)
74{
75}
76

--- 19 unchanged lines hidden (view full) ---

96 else if (revent & POLLNVAL)
97 vncserver->detach();
98}
99
100/**
101 * VncServer
102 */
103VncServer::VncServer(const Params *p)
104 : SimObject(p), listenEvent(NULL), dataEvent(NULL), number(p->number),
105 dataFd(-1), _videoWidth(1), _videoHeight(1), clientRfb(0), keyboard(NULL),
106 mouse(NULL), sendUpdate(false), videoMode(VideoConvert::UnknownMode),
107 vc(NULL), captureEnabled(p->frame_capture), captureCurrentFrame(0),
108 captureLastHash(0), captureBitmap(0)
109{
110 if (p->port)
111 listen(p->port);
112
113 curState = WaitForProtocolVersion;
114
115 // currently we only support this one pixel format
116 // unpacked 32bit rgb (rgb888 + 8 bits of nothing/alpha)

--- 5 unchanged lines hidden (view full) ---

122 pixelFormat.truecolor = 1;
123 pixelFormat.redmax = 0xff;
124 pixelFormat.greenmax = 0xff;
125 pixelFormat.bluemax = 0xff;
126 pixelFormat.redshift = 16;
127 pixelFormat.greenshift = 8;
128 pixelFormat.blueshift = 0;
129
130 if (captureEnabled) {
131 // remove existing frame output directory if it exists, then create a
132 // clean empty directory
133 const string FRAME_OUTPUT_SUBDIR = "frames_" + name();
134 simout.remove(FRAME_OUTPUT_SUBDIR, true);
135 captureOutputDirectory = simout.createSubdirectory(
136 FRAME_OUTPUT_SUBDIR);
137 }
138
139 DPRINTF(VNC, "Vnc server created at port %d\n", p->port);
140}
141
142VncServer::~VncServer()
143{
144 if (dataFd != -1)
145 ::close(dataFd);
146

--- 313 unchanged lines hidden (view full) ---

460 msg.namelen = 2;
461 msg.namelen = htobe(msg.namelen);
462 memcpy(msg.name, "M5", 2);
463
464 write(&msg);
465 curState = NormalPhase;
466}
467
468
469void
470VncServer::setPixelFormat()
471{
472 DPRINTF(VNC, "Received pixel format from client message\n");
473
474 PixelFormatMessage pfm;
475 read1((uint8_t*)&pfm, sizeof(PixelFormatMessage));
476

--- 126 unchanged lines hidden (view full) ---

603
604}
605
606
607void
608VncServer::sendFrameBufferUpdate()
609{
610
611 if (!clientRfb || dataFd <= 0 || curState != NormalPhase || !sendUpdate) {
612 DPRINTF(VNC, "NOT sending framebuffer update\n");
613 return;
614 }
615
616 assert(vc);
617
618 // The client will request data constantly, unless we throttle it
619 sendUpdate = false;

--- 18 unchanged lines hidden (view full) ---

638 fbr.width = htobe(fbr.width);
639 fbr.height = htobe(fbr.height);
640 fbr.encoding = htobe(fbr.encoding);
641
642 // send headers to client
643 write(&fbu);
644 write(&fbr);
645
646 assert(clientRfb);
647
648 uint8_t *tmp = vc->convert(clientRfb);
649 write(tmp, videoWidth() * videoHeight() * sizeof(uint32_t));
650 delete [] tmp;
651
652}
653
654void
655VncServer::sendFrameBufferResized()
656{
657 assert(clientRfb && dataFd > 0 && curState == NormalPhase);
658 DPRINTF(VNC, "Sending framebuffer resize\n");
659
660 FrameBufferUpdate fbu;
661 FrameBufferRect fbr;
662
663 fbu.type = ServerFrameBufferUpdate;
664 fbu.num_rects = 1;
665 fbr.x = 0;

--- 13 unchanged lines hidden (view full) ---

679 // send headers to client
680 write(&fbu);
681 write(&fbr);
682
683 // No actual data is sent in this message
684}
685
686void
687VncServer::setFrameBufferParams(VideoConvert::Mode mode, int width, int height)
688{
689 DPRINTF(VNC, "Updating video params: mode: %d width: %d height: %d\n", mode,
690 width, height);
691
692 if (mode != videoMode || width != videoWidth() || height != videoHeight()) {
693 videoMode = mode;
694 _videoWidth = width;
695 _videoHeight = height;
696
697 if (vc)
698 delete vc;
699
700 vc = new VideoConvert(mode, VideoConvert::rgb8888, videoWidth(),
701 videoHeight());
702
703 if (captureEnabled) {
704 // create bitmap of the frame with new attributes
705 if (captureBitmap)
706 delete captureBitmap;
707
708 assert(clientRfb);
709 captureBitmap = new Bitmap(videoMode, width, height, clientRfb);
710 assert(captureBitmap);
711 }
712
713 if (dataFd > 0 && clientRfb && curState == NormalPhase) {
714 if (supportsResizeEnc)
715 sendFrameBufferResized();
716 else
717 // The frame buffer changed size and we can't update the client
718 detach();
719 }
720 }
721}
722
723// create the VNC server object
724VncServer *
725VncServerParams::create()
726{
727 return new VncServer(this);
728}
729
730void
731VncServer::captureFrameBuffer()
732{
733 assert(captureBitmap);
734
735 // skip identical frames
736 uint64_t new_hash = captureBitmap->getHash();
737 if (captureLastHash == new_hash)
738 return;
739 captureLastHash = new_hash;
740
741 // get the filename for the current frame
742 char frameFilenameBuffer[64];
743 snprintf(frameFilenameBuffer, 64, "fb.%06d.%lld.bmp.gz",
744 captureCurrentFrame, static_cast<long long int>(curTick()));
745 const string frameFilename(frameFilenameBuffer);
746
747 // create the compressed framebuffer file
748 ostream *fb_out = simout.create(captureOutputDirectory + frameFilename,
749 true);
750 captureBitmap->write(fb_out);
751 simout.close(fb_out);
752
753 ++captureCurrentFrame;
754}