What is the role of grpc::AuthContext, consumed_auth_metadata and response_metadata in Process()? - c++

I've built a class that inherit grpc::AuthMetadataProcessor for assign and checking tokens for RPCs taking a cue from this question on stack-overflow and this implementation in the official GitHub repo.
A part from this block comment in auth_metadata_processor.h
/// context is read/write: it contains the properties of the channel peer and
/// it is the job of the Process method to augment it with properties derived
/// from the passed-in auth_metadata.
/// consumed_auth_metadata needs to be filled with metadata that has been
/// consumed by the processor and will be removed from the call.
/// response_metadata is the metadata that will be sent as part of the
/// response.
/// If the return value is not Status::OK, the rpc call will be aborted with
/// the error code and error message sent back to the client.
I'm having an hard time finding more resources on the use of those 3 object.
Why I need to put consumed metadata inside consumed_auth_metadata? Security purposes maybe? Convenience purposes for me, maybe?
Why I need to put metadata inside response_metadata in order to let them readable by the RPC? Doesn't they (the metadatas) pass through anyway (except path, authority and encodings metadata)?
What is the purpose of grpc::AuthContext::AddProperty() and grpc::AuthContext::SetPeerIdentityPropertyName() methods?
The only thing that I'm pretty sure I've understood is that const InputMetadata& auth_metadata contains all the metadata brought by the call like :path, :authority, encodings, user-agent and custom metadatas and some of them will not be visible inside the RPC implementation.

Related

Can a chaincode interact with other chaincode?

I am trying to write an application with hyper-ledger and I was looking for a way to communicate with chain-code from another chain-code. Is that possible in hyper-ledger?
I know its possible in etherum to communicate with other smart contracts but is the same possible in hyperledger. I could not find any related links related to same. Any suggestions on how to approach this will be really helpful.
I checked out Writing Your First Application, but I could not find the suitable explanation for same.
Chaincode could interact with other chaincode by means of leveraging existing API of ChaincodeStubInterface, e.g.:
// InvokeChaincode locally calls the specified chaincode `Invoke` using the
// same transaction context; that is, chaincode calling chaincode doesn't
// create a new transaction message.
// If the called chaincode is on the same channel, it simply adds the called
// chaincode read set and write set to the calling transaction.
// If the called chaincode is on a different channel,
// only the Response is returned to the calling chaincode; any PutState calls
// from the called chaincode will not have any effect on the ledger; that is,
// the called chaincode on a different channel will not have its read set
// and write set applied to the transaction. Only the calling chaincode's
// read set and write set will be applied to the transaction. Effectively
// the called chaincode on a different channel is a `Query`, which does not
// participate in state validation checks in subsequent commit phase.
// If `channel` is empty, the caller's channel is assumed.
InvokeChaincode(chaincodeName string, args [][]byte, channel string) pb.Response
Here is an example of how you can use it:
response := stub.InvokeChaincode(chaincodeName, chainCodeArgs, channelName)
Of course peer should have rights and chaincode installed.

Encrypt and sign a message using Microsoft Security Support Provider Interface (SSPI)

I want to use Microsoft's Security Support Provider Interface (SSPI) in a Windows Domain environment (with Kerberos) to send encrypted and signed messages between two entities (in C++).
Based on the documentation within the MSDN, there are the two functions MakeSignature() and EncryptMessage() [1] but the documentation as well as the example code [2] do not explicitly anwser the question of how to send data encrypted and signed (according to encrypt-than-mac).
Can anyone confirm that I have to use manually invoke EncryptMessage() and MakeSignature() in sequence to get to the desired result? Or do I miss something there and EncryptMessage() has a way to directly create a signature of the encrypted data?
[1] MSDN documentation of EncryptMessage() and MakeSignature()
https://msdn.microsoft.com/en-us/library/windows/desktop/aa378736(v=vs.85).aspx
https://msdn.microsoft.com/en-us/library/windows/desktop/aa375378(v=vs.85).aspx
[2] MSDN Example Code
https://msdn.microsoft.com/en-us/library/windows/desktop/aa380531(v=vs.85).aspx
---- Reply to Remus Rusanu's answer 2017-03-09 ---------------------------
Thanks #Remus Rusanu for your answer, I didn't take the GSSAPI interoperability document into account yet.
Here it is stated that "GSS_Wrap and GSS_Unwrap are used for both integrity and privacy with the use of privacy controlled by the value of the "conf_flag" argument." and that "The SSPI equivalent to GSS_Wrap is EncryptMessage (Kerberos) for both integrity and privacy".
You said that "EncryptMessage [...] will do the signing too, if the negotiated context requires it.". This means for me, that the at least the following fContextReq flags need to be set for InitializeSecurityContext():
ISC_REQ_CONFIDENTIALITY
ISC_REQ_INTEGRITY
Can you (or somebody else) can confirm this?
---- Update 2017-03-16 ----------------------------------------------------------------
After further research I came up with the following insights:
The Kerberos specific EncryptMessage() function does not provide message integrity, regardless of how the Securitycontext was initialized.
The general EncryptMessage() and general DecryptMessage functions support the feature of creating and verifying the message's integrity because there exists some supporting Security Support Providers (SSPs) - but Kerberos does not.
If DecryptMessage would check the message's integrity, there must be a respective error return code in case of a modified message. The general DecryptMessage interface lists the error code "SEC_E_MESSAGE_ALTERED" which is described as "The message has been altered. Used with the Digest and Schannel SSPs.".
The specific DecryptMessage interface for the SSPs Digest and Schannel lists the SEC_E_MESSAGE_ALTERED - but the Kerberos DecryptMessage does not.
Within the parameter description of the general EncryptMessage's documentation, the term 'signature' is used only regarding the Digest SSP: "When using the Digest SSP, there must be a second buffer of type
SECBUFFER_PADDING or SEC_BUFFER_DATA to hold signature information".
MakeSignature does not create a digital signature according to Wikipedia's definition (authenticity + non-repudiation + integrity). MakeSignature creates a cryptographic hash to provide message integrity.
The name of the MakeSignature() function leads to the idea that SSPI creates a digital signature (authenticity + non-repudiation + integrity) but the MakeSignature documentation explains that only a cryptographic checksum is created (providing integrity): "The MakeSignature function generates a cryptographic checksum of the message, and also includes sequencing information to prevent message loss or insertion."
The VerifySignature documentation helps as well to clarify SSPI's terminology: "Verifies that a message signed by using the MakeSignature function was received in the correct sequence and has not been modified."
From (1) and (2) it follows that one needs to invoke EncryptData() and afterwards MakeSignature() (for the ciphertext) to achieve confidentiality and integrity.
Hope that my self-answer will help someone at some point in time ;)
If someone has something to add or correct in my answer, please reply and help to improve the information collected here!
If I remember correctly you only call EncryptMessage/DecryptMessage and this will do the signing too, if the negotiated context requires it. For example if you look at SSPI/Kerberos Interoperability with GSSAPI it states that EncryptMessagepairs with GSS_Unwrap and DecryptMessage pairs with GSS_Wrap, without involving MakeSignature. The example in the link also shows that you must supply 3 SecBuffer structures (SECBUFFER_TOKEN, SECBUFFER_DATA and SECBUFFER_PADDING, the last I think is optional) to EncryptMessage and 2 for DecryptMessage. The two complementary examples at Using SSPI with a Windows Sockets Server and Using SSPI with a Windows Sockets Client give full functional message exchange and you can also see that MakeSignature/VerifySignature are never called, the signature is handled by Encrypt/Decrypt and is placed in the 'security token' header or trailer (where to it goes on the wire is not specified by SSPI/SPNego/Kerberos, this is not TLS/Schannel...).
If you want to create a GSS Wrap token with only a signature (not encrypted), pass KERB_WRAP_NO_ENCRYPT as the qop value to EncryptMessage. The signed wrap token includes the payload and the signature.
MakeSignature creates a GSS MIC token - which is only the signature and does not include the payload. You can use this with application protocols that require a detached signature.

Wowza: Modifying a Stream as it is playing?

It seems like this must be happening in many different contexts such as adding subtitles. What I want to do is grab a frame, change some feature within it and then "put it back" so that the end user sees this change. I think I know how to grab and modify the frame but re-inserting it into the stream I do not see how to do. Would appreciate a link or code.
On a live stream, there are a few things to consider depending on what the end goal might be. If it's true packet / frame level manipulation you would likely need to make the modification and set the output to a new stream (source remains unscathed but new stream has the modification). Modifying the stream inline will be very problematic.
Packet level modification using IMediaStreamLivePacketNotify
You can implement the IMediaStreamLivePacketNotify interface to handle new packets and modify them as necessary. Example implementation:
private class PacketListener implements IMediaStreamLivePacketNotify
{
#Override
public void onLivePacket(IMediaStream stream, AMFPacket packet)
{
// handle packet modifications
}
}
Upon modifying the packet you could publish it to a secondary stream that you publish through the Publisher object.
Publisher.createInstance(vhost, appName, appInstName);
The publisher contains functionality to add A/V data to your new stream:
switch (packet.getType())
{
case IVHost.CONTENTTYPE_AUDIO:
publisher.addAudioData(packet.getData(), packet.getAbsTimecode());
break;
case IVHost.CONTENTTYPE_VIDEO:
publisher.addVideoData(packet.getData(), packet.getAbsTimecode());
break;
case IVHost.CONTENTTYPE_DATA:
case IVHost.CONTENTTYPE_DATA3:
publisher.addDataData(packet.getData(), packet.getAbsTimecode());
}
There is similar functionality within the Duplicate Streams module for a broader look at this implementation.
Packet level modification using getPlayPackets()
You could also look at the IMediaStream object and leverage the IMediaStream.getPlayPackets() functionality. Then you can obtain the packets and modify as needed in a corresponding thread that continually processes the inbound stream. Thereafter, you could use the Publisher object to publish the new stream (similar to the above).
Metadata injection
However, if you are just looking to inject some metadata the process becomes much more basic. You can modify the AMFDataList within the source stream to include the new meta information.
Adding onto the stream
If you are looking to add data onto the inline stream (vs modifying it) you could simply add it via the ImediaStream object:
IMediaStream.addAudioData(..)

Thread Safety in Jax-WS Request-Response Payload Logging

I am working on a SoapHandler implementation. Basically my aim is to get both request and response payloads and insert them to the database.
Although I can get the request and response payloads, I couldn't make sure if my code is working thread-safe. In other words, I am not sure if responses match with the proper requests.
public boolean handleMessage(SOAPMessageContext mContext) {
boolean isResponse = (Boolean) mContext
.get(MessageContext.MESSAGE_OUTBOUND_PROPERTY);
if (!isResponse) {
try {
mContext.put("currentStream", new ByteArrayOutputStream());
mContext.getMessage().writeTo((OutputStream) mContext.get("currentStream"));
} catch (SOAPException | IOException e) {
e.printStackTrace();
}
} else {
try {
mContext.getMessage().writeTo(
(OutputStream) mContext.get("currentStream"));
System.out.println(((OutputStream) mContext.get("currentStream"))
.toString());
((OutputStream) mContext.get("currentStream")).flush();
} catch (SOAPException | IOException e) {
e.printStackTrace();
}
}
return true;
}
I found this in JCP specs:
9.3.3 Handler Implementation Considerations
Handler instances may be pooled by a JAX-RPC runtime system. All instances of a specific handler are
considered equivalent by a JAX-RPC runtime system and any instance may be chosen to handle a particular
message. Different handler instances may be used to handle each messages of an MEP. Different threads
may be used for each handler in a handler chain, for each message in an MEP or any combination of the
two. Handlers should not rely on thread local state to share information. Handlers should instead use the
message context, see section 9.4.
9.4 Message Context
Handlers are invoked with a message context that provides methods to access and modify inbound and
outbound messages and to manage a set of properties.
Different types of handler are invoked with different types of message context. Sections 9.4.1 and 9.4.2
describe MessageContext and LogicalMessageContext respectively. In addition, JAX-RPC bindings 12
may define a message context subtype for their particular protocol binding that provides access to protocol
specific features. Section10.3 describes the message context subtype for the JAX-RPC SOAP binding.
http://download.oracle.com/otn-pub/jcp/jaxrpc-2.0-edr2-spec-oth-JSpec/jaxrpc-2_0-edr2-spec.pdf?AuthParam=1431341511_1ac4403a34d7db108bce79eda126df49
Does this imply that a new MessageContext object is created for each request (in which case I think the code will be thread safe), or the same MessageContext object can be used for multiple requests (then my code will not be thread safe).
Any help / alternative solution will be appreciated.
Rule of thumb: a FooContext object is contextual by definition, relating to a specific execution context. EJBContext relating to a single EJB; FacesContext relating to a single Faces request context; SOAPMessageContext relating to a single SOAPMessage. From the JSR-109 documentation:
The container must share the same MessageContext instance across all Handler instances and the target endpoint that are invoked during a single request and response or fault processing on a specific node.
So, you can be sure that there's one new SOAPMessageContext instance per request. Within the context of a single request however, that instance is yours to mangle. So the question really is, what do you mean by "threadsafety"? Do you plan to have multiple threads processing a single SOAPMessageContext during each request? I don't recommend it
EDIT: While the specification doesn't state in black and white that a MessageContext is threadsafe, it's implied throughout the specification. The following is an excerpt from the section of the spec that states what's possible on a MessageContext, within a handler:
Handlers may manipulate the values and scope of properties within the message context as desired. E.g. ... a handler in a server-side SOAP binding might add application scoped properties tot he message context from the contents of a header in a request SOAP message...
SOAP handlers are passed a SOAPMessageContext when invoked. SOAPMessageContext extends MessageContext with methods to obtain and modify the SOAP message payload
The specification won't be expecting programmers to modify the content of the context if it weren't safe to do so.

understanding RProperty IPC communication

i'm studying this source base. Basically this is an Anim server client for Symbian 3rd edition for the purpose of grabbing input events without consuming them in a reliable way.
If you spot this line of the server, here it is basically setting the RProperty value (apparently to an increasing counter); it seems no actual processing of the input is done.
inside this client line, the client is supposed to be receiving the notification data, but it only calls Attach.
my understanding is that Attach is only required to be called once, but is not clear in the client what event is triggered every time the server sets the RProperty
How (and where) is the client supposed to access the RProperty value?
After Attaching the client will somewhere Subscribe to the property where it passes a TRequestStatus reference. The server will signal the request status property via the kernel when the asynchronous event has happened (in your case the property was changed). If your example source code is implemented in the right way, you will find an active object (AO; CActive derived class) hanging around and the iStatus of this AO will be passed to the RProperty API. In this case the RunL function of the AO will be called when the property has been changed.
It is essential in Symbian to understand the active object framework and quite few people do it actually. Unfortunately I did not find a really good description online (they are explained quite well in Symbian OS Internals book) but this page at least gives you a quick example.
Example
In the ConstructL of your CMyActive subclass of CActive:
CKeyEventsClient* iClient;
RProperty iProperty;
// ...
void CMyActive::ConstructL()
{
RProcess myProcess;
TSecureId propertyCategory = myProcess.SecureId();
// avoid interference with other properties by defining the category
// as a secure ID of your process (perhaps it's the only allowed value)
TUint propertyKey = 1; // whatever you want
iClient = CKeyEventsClient::NewL(propertyCategory, propertyKey, ...);
iClient->OpenNotificationPropertyL(&iProperty);
// ...
CActiveScheduler::Add(this);
iProperty.Subscribe(iStatus);
SetActive();
}
Your RunL will be called when the property has been changed:
void CMyActive::RunL()
{
if (iStatus.Int() != KErrCancel) User::LeaveIfError(iStatus.Int());
// forward the error to RunError
// "To ensure that the subscriber does not miss updates, it should
// re-issue a subscription request before retrieving the current value
// and acting on it." (from docs)
iProperty.Subscribe(iStatus);
TInt value; // this type is passed to RProperty::Define() in the client
TInt err = iProperty.Get(value);
if (err != KErrNotFound) User::LeaveIfError(err);
SetActive();
}