sensepost / ruler

A tool to abuse Exchange services

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

The way to get PR_BODY or PR_MESSAGE_ATTACHMENTS

ysq110 opened this issue · comments

Hi

I'm interesting about the great tool you create called "Ruler", but i met some problems. Some properties can not be fetched correctly, like PR_BODY (0x1000) or PR_MESSAGE_ATTACHMENTS (0x0E13). Is there a way to help me solve these questions?

Thank you very much!

Hi!

It seems like you are trying the forms functionality. Could you please provide the error output? I haven't seen an issue with those properties before. There are a LARGE number of things that could be causing it unfortunately :(

There is a function named "GetMessage" in mapi/mapi.go , when we tried to get properties like "PR_BODY (0x1000)" or "PR_MESSAGE_ATTACHMENTS (0x0E13)" from messages in "INBOX" folder, it could not return the correct value of these properties.
example
After searching the reference of MAPI funcions, fetching PR_BODY we supposed to get an UTF-8 string (the same as PR_TITLE), but it returns nothing. After that, we pass an empty column as propertytag to fetch all properies of the message and print each propery's value type, but we still can't find it.
Could you tell me your email address, so i can send more pics and infomations to you :-)

Oh brilliant, you are using the library directly! I thought this was an error coming out of ruler directly.

It seems like you have gotten as far as opening the message, so you understand the concept of input/output handles used by mapi. The best example of getting a message body I've implemented is available here: https://github.com/sensepost/liniaal/blob/master/liniaal.go#L151-L163

//fetch full message
columns := make([]mapi.PropertyTag, 1)
columns[0] = mapi.PidTagBody //Column for the Message Body containing our payload

buff, err := mapi.GetMessageFast(folderid, messageid, columns)
if err != nil {
    continue
}
//convert buffer to rows
messagerows := mapi.DecodeBufferToRows(buff.TransferBuffer, columns)

stop = false
payload := fromUnicode(messagerows[0].ValueArray[:len(messagerows[0].ValueArray)-4])

if payload == "" {
    continue
}

You'll note that it uses GetMessageFast rather than the normal GetMessage - the reason for this being that GetMessage works well for small messages/fields - such as getting the subject etc - but as soon as the message size is larger than "one packet" an empty buffer gets returned (which matches with what you are seeing 😄)

The example above ends up giving you the Unicode body of the message, I can't recall the reason for this.

happy to help with this, super curious to hear what you are building, I didn't think anyone would ever use the library! stalmans protonmail.com