Commit 6d3161ff authored by Steven Murray's avatar Steven Murray
Browse files

Added the new message castor::messages::LabelError

parent 26425b11
......@@ -81,6 +81,15 @@ namespace castor {
std::ostringstream& getMessage() {
return m_message;
}
/**
* Get the value of m_message
* A message explaining why this exception was raised
* @return the value of m_message
*/
const std::ostringstream& getMessage() const {
return m_message;
}
/**
* Get the value of m_message as a sting, for const-c orrectness
......
......@@ -68,6 +68,8 @@ const char *castor::messages::msgTypeToString(const MsgType msgType) throw() {
return "TapeUnmounStarted";
case MSG_TYPE_TAPEUNMOUNTED:
return "TapeUnmounted";
case MSG_TYPE_LABELERROR:
return "LabelError";
default:
return "Unknown";
}
......
......@@ -51,7 +51,8 @@ enum MsgType {
MSG_TYPE_TAPEMOUNTEDFORMIGRATION,
MSG_TYPE_TAPEMOUNTEDFORRECALL,
MSG_TYPE_TAPEUNMOUNTSTARTED,
MSG_TYPE_TAPEUNMOUNTED
MSG_TYPE_TAPEUNMOUNTED,
MSG_TYPE_LABELERROR
};
enum ProtocolVersion {
......
// This file is part of the Castor project.
// See http://castor.web.cern.ch/castor
//
// Copyright (C) 2003 CERN
// 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 2
// 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, write to the Free Software
// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
//
// @author Castor Dev team, castor-dev@cern.ch
package castor.messages;
message LabelError {
// The unit name of the drive
required string unitname = 1;
// The error code
required uint32 code = 2;
// The error message
required string message = 3;
}
......@@ -135,6 +135,16 @@ public:
virtual void notifyHeartbeat(const std::string &unitName,
const uint64_t nbBytesMoved) = 0;
/**
* Notifies the tapeserverd daemon that a label session has encountered the
* specified error.
*
* @param unitName The unit name of the tape drive.
* @param labelEx The error encountered by the label session.
*/
virtual void labelError(const std::string &unitName,
const castor::exception::Exception &labelEx) = 0;
}; // class TapeserverProxy
} // namespace messages
......
......@@ -97,3 +97,10 @@ void castor::messages::TapeserverProxyDummy::tapeUnmounted(
void castor::messages::TapeserverProxyDummy::
notifyHeartbeat(const std::string &unitName, const uint64_t nbBlocksMoved) {
}
//------------------------------------------------------------------------------
// labelError
//------------------------------------------------------------------------------
void castor::messages::TapeserverProxyDummy::labelError(
const std::string &unitName, const castor::exception::Exception &labelEx) {
}
......@@ -133,6 +133,17 @@ public:
*/
void notifyHeartbeat(const std::string &unitName,
const uint64_t nbBlocksMoved);
/**
* Notifies the tapeserverd daemon that a label session has encountered the
* specified error.
*
* @param unitName The unit name of the tape drive.
* @param labelEx The error encountered by the label session.
*/
void labelError(const std::string &unitName,
const castor::exception::Exception &labelEx);
}; // class TapeserverProxyDummy
} // namespace messages
......
......@@ -23,6 +23,7 @@
#include "castor/messages/Heartbeat.pb.h"
#include "castor/messages/Header.pb.h"
#include "castor/messages/Constants.hpp"
#include "castor/messages/LabelError.pb.h"
#include "castor/messages/messages.hpp"
#include "castor/messages/MigrationJobFromTapeGateway.pb.h"
#include "castor/messages/MigrationJobFromWriteTp.pb.h"
......@@ -541,3 +542,59 @@ castor::messages::Frame castor::messages::TapeserverProxyZmq::
throw ex;
}
}
//------------------------------------------------------------------------------
// labelError
//------------------------------------------------------------------------------
void castor::messages::TapeserverProxyZmq::labelError(
const std::string &unitName, const castor::exception::Exception &labelEx) {
try {
const Frame rqst = createLabelErrorFrame(unitName, labelEx);
sendFrame(m_tapeserverSocket, rqst);
ReturnValue reply;
recvTapeReplyOrEx(m_tapeserverSocket, reply);
if(0 != reply.value()) {
// Should never get here
castor::exception::Exception ex;
ex.getMessage() << "Received an unexpected return value"
": expected=0 actual=" << reply.value();
throw ex;
}
} catch(castor::exception::Exception &ne) {
castor::exception::Exception ex;
ex.getMessage() <<
"Failed to notify tapeserver of label-session error: " <<
"unitName=" << unitName << ": " <<
ne.getMessage().str();
throw ex;
}
}
//------------------------------------------------------------------------------
// createLabelErrorFrame
//------------------------------------------------------------------------------
castor::messages::Frame castor::messages::TapeserverProxyZmq::
createLabelErrorFrame(const std::string &unitName,
const castor::exception::Exception &labelEx) {
try {
Frame frame;
frame.header = messages::protoTapePreFillHeader();
frame.header.set_msgtype(messages::MSG_TYPE_LABELERROR);
frame.header.set_bodysignature("PIPO");
LabelError body;
body.set_unitname(unitName);
body.set_code(labelEx.code());
body.set_message(labelEx.getMessage().str());
frame.serializeProtocolBufferIntoBody(body);
return frame;
} catch(castor::exception::Exception &ne) {
castor::exception::Exception ex;
ex.getMessage() << "Failed to create LabelError frame: " <<
ne.getMessage().str();
throw ex;
}
}
......@@ -143,6 +143,16 @@ public:
void notifyHeartbeat(const std::string &unitName,
const uint64_t nbBlocksMoved);
/**
* Notifies the tapeserverd daemon that a label session has encountered the
* specified error.
*
* @param unitName The unit name of the tape drive.
* @param LabelEx The error encountered by the label session.
*/
void labelError(const std::string &unitName,
const castor::exception::Exception &labelEx);
private:
/**
......@@ -262,6 +272,16 @@ private:
Frame createHeartbeatFrame(const std::string &unitName,
const uint64_t nbBlocksMoved);
/**
* Creates a frame containing a LabelError message.
*
* @param unitName The unit name of the tape drive.
* @param LabelEx The error encountered by the label session.
* @return The frame.
*/
Frame createLabelErrorFrame(const std::string &unitName,
const castor::exception::Exception &labelEx);
}; // class TapeserverProxyZmq
} // namespace messages
......
......@@ -153,3 +153,11 @@ bool castor::tape::tapeserver::daemon::DriveCatalogueLabelSession::
tapeIsBeingMounted() const throw() {
return false;
}
//-----------------------------------------------------------------------------
// receivedLabelError
//-----------------------------------------------------------------------------
void castor::tape::tapeserver::daemon::DriveCatalogueLabelSession::
receivedLabelError(const castor::exception::Exception &labelEx) {
m_labelErrors.push_back(labelEx);
}
......@@ -29,6 +29,8 @@
#include "castor/tape/tapeserver/daemon/ProcessForkerProxy.hpp"
#include "castor/tape/utils/DriveConfig.hpp"
#include <list>
namespace castor {
namespace tape {
namespace tapeserver {
......@@ -127,6 +129,13 @@ public:
*/
bool tapeIsBeingMounted() const throw();
/**
* To be called if the label session has sent tapserverd a label error.
*
* @param labelEx The label error.
*/
void receivedLabelError(const castor::exception::Exception &labelEx);
protected:
/**
......@@ -173,6 +182,11 @@ private:
*/
const int m_labelCmdConnection;
/**
* List of label errors receved from the label session.
*/
std::list<castor::exception::Exception> m_labelErrors;
}; // class DriveCatalogueLabelSession
} // namespace daemon
......
......@@ -64,33 +64,37 @@ castor::tape::tapeserver::daemon::LabelSession::LabelSession(
//------------------------------------------------------------------------------
castor::tape::tapeserver::daemon::Session::EndOfSessionAction
castor::tape::tapeserver::daemon::LabelSession::execute() {
std::ostringstream task;
task << "label tape " << m_request.vid << " for gid=" << m_request.gid <<
" uid=" << m_request.uid << " in drive " << m_request.drive;
log::Param params[] = {
try {
log::Param params[] = {
log::Param("uid", m_request.uid),
log::Param("gid", m_request.gid),
log::Param("vid", m_request.vid),
log::Param("drive", m_request.drive),
log::Param("dgn", m_request.dgn)};
performPreMountChecks();
mountTape();
std::auto_ptr<castor::tape::tapeserver::drives::DriveInterface> drive =
getDriveObject();
waitUntilTapeLoaded(drive.get(), 60); // 60 = 60 seconds
checkTapeIsWritable(drive.get());
labelTheTape(drive.get());
m_log(LOG_INFO, "The tape has been successfully labeled", params);
drive->unloadTape();
m_log(LOG_INFO, "The tape has been successfully unloaded after labeling",
params);
m_rmc.unmountTape(m_request.vid, m_driveConfig.librarySlot);
m_log(LOG_INFO, "The tape has been successfully unmounted after labeling",
params);
performPreMountChecks();
mountTape();
std::auto_ptr<castor::tape::tapeserver::drives::DriveInterface> drive =
getDriveObject();
waitUntilTapeLoaded(drive.get(), 60); // 60 = 60 seconds
checkTapeIsWritable(drive.get());
labelTheTape(drive.get());
m_log(LOG_INFO, "The tape has been successfully labeled", params);
drive->unloadTape();
m_log(LOG_INFO, "The tape has been successfully unloaded after labeling",
params);
m_rmc.unmountTape(m_request.vid, m_driveConfig.librarySlot);
m_log(LOG_INFO, "The tape has been successfully unmounted after labeling",
params);
return MARK_DRIVE_AS_UP;
} catch(castor::exception::Exception &ne) {
m_tapeserver.labelError(m_request.drive, ne);
return MARK_DRIVE_AS_UP;
castor::exception::Exception ex;
ex.getMessage() << "Failed to label tape: " << ne.getMessage().str();
throw ex;
}
}
//------------------------------------------------------------------------------
......
......@@ -23,6 +23,7 @@
#include "castor/messages/Constants.hpp"
#include "castor/messages/Exception.pb.h"
#include "castor/messages/Header.pb.h"
#include "castor/messages/LabelError.pb.h"
#include "castor/messages/messages.hpp"
#include "castor/messages/MigrationJobFromTapeGateway.pb.h"
#include "castor/messages/MigrationJobFromWriteTp.pb.h"
......@@ -196,6 +197,9 @@ castor::messages::Frame castor::tape::tapeserver::daemon::TapeMessageHandler::
case messages::MSG_TYPE_MIGRATIONJOBFROMWRITETP:
return handleMigrationJobFromWriteTp(rqst);
case messages::MSG_TYPE_LABELERROR:
return handleLabelError(rqst);
case messages::MSG_TYPE_RECALLJOBFROMREADTP:
return handleRecallJobFromReadTp(rqst);
......@@ -245,6 +249,37 @@ castor::messages::Frame castor::tape::tapeserver::daemon::TapeMessageHandler::
}
}
//------------------------------------------------------------------------------
// handleLabelError
//------------------------------------------------------------------------------
castor::messages::Frame castor::tape::tapeserver::daemon::TapeMessageHandler::
handleLabelError(const messages::Frame &rqst) {
m_log(LOG_DEBUG, "Handling LabelError message");
try {
castor::messages::LabelError rqstBody;
rqst.parseBodyIntoProtocolBuffer(rqstBody);
castor::exception::Exception labelEx(rqstBody.code());
labelEx.getMessage() << rqstBody.message();
log::Param params[] = {
log::Param("code", labelEx.code()),
log::Param("message", labelEx.getMessage().str())};
m_log(LOG_INFO, "Received LabelError", params);
DriveCatalogueEntry &drive =
m_driveCatalogue.findDrive(rqstBody.unitname());
drive.getLabelSession().receivedLabelError(labelEx);
const messages::Frame reply = createReturnValueFrame(0);
return reply;
} catch(castor::exception::Exception &ne) {
castor::exception::Exception ex;
ex.getMessage() << "Failed to handle LabelError message: " <<
ne.getMessage().str();
throw ex;
}
}
//------------------------------------------------------------------------------
// handleMigrationJobFromTapeGateway
//------------------------------------------------------------------------------
......
......@@ -175,6 +175,14 @@ private:
*/
messages::Frame handleHeartbeat(const messages::Frame &rqst);
/**
* Handles the specified request.
*
* @param rqst The request.
* @return The reply.
*/
messages::Frame handleLabelError(const messages::Frame &rqst);
/**
* Handles the specified request.
*
......
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment