AIM/Oscar Protocol Specification: Section 2: AIM Commands



2.0 AIM Commands

Everything in the AIM protocol is embodied in AIM commands. The division is not of packets because more than one command may be sent in any one packet, depending on the transmit timing, etc. Commands are an abstraction above packets, and leads to the definition of the FLAP protocol below.

Below is an attempt to generalize the layout of all AIM commands. The acronyms used are those used by the AIM client and the AIM divison of AOL as defined in the document at http://www.aim.aol.com/javadev/terminology.html. Please refer to that document if the explanations listed here are not complete enough for you.

Fig 2.1 Generalized Command Structure
FLAP
  • Command Start (byte: 0x2a)
  • Channel ID (byte)
  • Sequence Number (word)
  • Data Field Length (word)
Data Field
  • Usually SNAC Data (variable)
2.1 FLAP

The FLAP is the protocol that sits at the bottom of everything communicated across AIM channels. This generally makes up the first 6 bytes of every AIM command. If this protocol is not obeyed, the OSCAR server will disconnect the offending client immediatly upon reception of a malformed command. This is not helpful for debuging, to say the least.

2.1.1 FLAP: Headers

Contained in the FLAP headers are: (in order of appearance)

  • Command-Start [byte] (always 0x2a)
  • Channel Identification [byte]
  • Sequence Number [word]
  • FLAP Data Field Length [word]

This is followed immediatly by an unterminated FLAP Data Field, which concludes the FLAP command.

2.1.2 FLAP: Data Field

Normally, the FLAP Data Field contains a SNAC. The FLAP Data Field makes up the rest of the command (there is no FLAP-specific command terminator).

2.1.3 Sequence Numbers

Why AOL decided to use sequence numbering with TCP is beyond me. The retransmit and data integrity standards of TCP connections make this pointless. So, they're really just there for looks, though that doesn't mean that they can be incorrect. If the server gets an out-of-order command (according to the seqnums, not actual order), you will be disconnected.

The sequence number origins are picked quite randomly. There is no connection between the sequence number set from the server and the set from the client. Sequence numbers are always incremented upward (towards 0xFFFF) for each command sent. If the seqence number does reach 0xFFFF, it will wrap to 0x0000, for obvious reasons. If you start a new connection, it is recommended that a new sequence number origin is picked for that connection, for purposes of internal coherency. Sequence numbers are independent of channels: there's a single series of sequence numbers per TCP connection (per socket). See section 2.1.4 for more information.

2.1.4 Channels

Channels are the method used to multiplex seperate paths of communication across the same TCP socket. These are analogous to TCP/UDP port numbers. Four channels are currently used by OSCAR:

  • 0x01 - New Connection Negotiation
  • 0x02 - SNAC data (non connection-oriented data)
  • 0x03 - FLAP-level Error
  • 0x04 - Close Connection Negotiation

After a new connection (socket) is set up using channel 0x01, data should only be carried on channel 0x02, until a low-level FLAP error occurs (channel 0x03) or there is planned termination, which gets "negotiated" (on channel 0x04). Most live events processed during the lifespan of the client are done over channel 0x02. SNACs are never transmitted on any channel other than 0x02.

2.1.5 Features of FLAP

[Not yet.]

2.1.6 Thoughts on FLAP Implementation

The best way to read an incoming FLAP command is to first read only the starting 6 bytes (the FLAP headers). From these 6bytes, you can determine how many more bytes you need to read to complete the command, and how much memory you need to allocate to store it. Never read more or less than the number of bytes specified in the FLAP headers, or your read will result in a truncated or uninterpretable command. (If you read too much, you will probably end up reading the start of the next command, which is bad. Lost data is unacceptable in the AIM standard.)

Because every command must follow FLAP guidelines, I'd recommend using a low-level routine to add the FLAP headers (normally, this will be the "flush transmit queue" routine, so that addition of sequence numbers and the rest of the FLAP headers is done as close timewise as possible to the command being put on the wire). This is the best way to prevent out-of-order seqnums from getting used (which, as stated earlier, is quite fatal).

2.2 SNAC

The SNAC is the unit that sits immediatly above FLAP on most commands, and is the normal contents of the FLAP Data Field for channel 0x02. SNACs are only sent over channel 0x02. Data sent across other channels are not considered complete SNACs. There can be only one SNAC per FLAP command.

SNACs are generalized into the following format:

PositionSizePurpose
1wordFamily ID
3wordSubType ID
5byteFlags[0]
6byteFlags[1]
7dwordRequest ID
11variableSNAC Data

There is no formal declaration of the length of the SNAC data portion (that information must be assumed from the FLAP headers).

"Families", identified by the "Family ID", constitute a group of services. These are usually quite large groups.

Subtypes are a subdivision of the Families. Each subtype ID is different depending on the specific service or information provided in the data section.

Flags are completely optional. They're very rarely used, if at all.

Request IDs are 32bit values used to identify non-atomic information. The client can generate completely random reqid's as long as it remembers what the request was for. Often, though, the results of the SNAC are irrelevent, and the reqid's can be forgotten. But, in information-requestion SNACs, it is imparative you remember the reqid you sent because that's the only way to link it to the response! If this is not done, it will be impossible to have more than one pending request of the same SNAC subtype (which is unlikely at best). For server-initiated SNACs, the reqid is ORed with the fixed value -2147483648, and count up to zero from than from zero.

Table 2.2.1 lists all documented SNAC types and subtypes.

Table 2.2.1 Known SNACs
SubtypeSourceFunction
Family 0x0001: Generic Service Controls
0x0001Client or ServerError
0x0002ClientClient is now online and ready for normal function
0x0003ServerServer is now ready for normal functions
0x0004ClientRequest for new service (the server will redirect the client to a new host where the service is available)
0x0005ServerRedirect (response to subtype 0x0004 from client)
0x0006ClientRequest Rate Information (request rate at which client can send SNACs)
0x0007ServerRate information response (response to subtype 0x0006)
0x0008ClientRate Information Response Ack
0x000AServerRate information change
0x000BServerPause
0x000DServerResume
0x000EClientRequest information on the screen name you've been authenticated under.
0x000FServerInformation the screen name you've been authenticated under.
0x0010ServerEvil notification
0x0012ServerMigration notice/request
0x0013ServerMessage of the day
0x0014ClientSet Privacy flags
0x0015ServerWell known urls
0x0016ServerNo op
Family 0x0002: Location Services
0x0001Client or ServerError
0x0002ClientRequest rights information
0x0003ServerRights information
0x0004ClientSet user information
0x0005ClientRequest user information
0x0006ServerUser information
0x0007ClientWatcher sub request
0x0008ServerWatcher notification
Family 0x0003: Buddy List Management
0x0001Client or ServerError
0x0002ClientRequest rights information
0x0003ServerRights information
0x0004ClientAdd buddy to buddy list
0x0005ClientRemove buddy from buddy list
0x0006ClientWatcher list query
0x0007ServerWatcher list response
0x0008ClientWatcher sub request
0x0009ServerWatcher notification
0x000AServerReject notification
0x000BServerOncoming buddy
0x000CServerOffgoing buddy
Family 0x0004: Messaging
0x0001Client or ServerError
0x0002ClientAdd ICBM parameter
0x0003ClientRemove ICBM parameter
0x0004ClientRequest parameter information
0x0005ServerParameter information
0x0006ClientMessage from the client
0x0007ServerMessage to the client
0x0008ClientEvil request
0x0009ServerEvil reply
0x000AServerMissed calls
0x000BClient or ServerClient error
0x000CServerHost ack
Family 0x0005: Advertisments
0x0001Client or ServerError
0x0002ClientRequest advertisments
0x0003ServerAdvertisment data (GIFs)
Family 0x0006: Invitation and Client-to-Client
0x0002ClientInvite a friend to join AIM
0x0003ServerInvite a friend to join AIM ack
Family 0x0007: Administrative
0x0001ServerAdmin error
0x0002ClientInformation request
0x0003ServerInformation reply
0x0004ClientInformation change request
0x0005ServerInformation change reply
0x0006ClientAccount confirm request
0x0007ServerAccount confirm reply
0x0008ClientAccount delete request
0x0009ServerAccount delete reply
Family 0x0008: Popup Notices
0x0001Client or ServerError
0x0002ServerDisplay popup
Family 0x0009: BOS-specific
0x0001Client or ServerError
0x0002ClientRequest BOS Rights
0x0003ServerBOS Rights
0x0004ClientSet group permission mask
0x0005ClientAdd permission list entries
0x0006ClientDelete permission list entries
0x0007ClientAdd deny list entries
0x0008ClientDelete deny list entries
0x0009ServerBOS error
Family 0x000A: User Lookup
0x0001Client or ServerError (often Search Failed)
0x0002ClientSearch for screen name by email address
0x0003ServerSearch Response
Family 0x000B: Stats
0x0001Client or ServerError
0x0002ServerSet minimum report interval
0x0003ClientReport events
0x0004ServerReport ack
Family 0x000C: Translate
0x0001Client or ServerError
0x0002ClientTranslate request
0x0003ServerTranslate reply
Family 0x000D: Chat Navigation
0x0001Client or ServerError
0x0002ClientRequest chat rights
0x0003ClientRequest exchange information
0x0004ClientRequest room information
0x0005ClientRequest more room information
0x0006ClientRequest occupant list
0x0007ClientSearch for room
0x0008ClientCreate room
0x0009ServerNavigation information
Family 0x000E: Chat
0x0001Client or ServerError
0x0002ServerRoom information update
0x0003ServerUsers joined
0x0004ServerUsers left
0x0005ClientChannel message from client
0x0006ServerChannel message to client
0x0007ServerEvil request
0x0008ServerEvil reply
0x0009Client or ServerClient error
Family 0x0045: Unknown (Client Something?)
0x0002ClientAdd to notify list

2.2.1 Notes on SNACs

If you have more to add to the list, please do. These are the basics of OSCAR communication, so there's bound to be alot of them!

One last note on the subject: never eat SNACs. They're extremely fattening, no matter what the National SNAC Council's television commercials tell you about them. Also, they have been known to cause your limbs to start FLAPing, which often results in unannounced levetation.

2.3 TLVs

TLVs are a very convenient and efficient method of putting data into an organized format, esp variable length strings, etc. TLV litterally stands for "Type, Length, Value". And that's exactly what it is: a 16bit Type code, a 16bit value for the length of the Value field, and then the actual data in the Value field (variable length).

TLVs can be be in SNACs, but thats not required. TLVs often are used directly in the FLAP Data Field, but normally are inside of SNACs. No more than one TLV of each Type code may exist in a single FLAP command (SNAC or not). TLVs must follow the strict tuple-rule, or they're really not TLVs, they're raw data.

TLVs are a big win. They make sending a variable length string like, eg, "afritz@iname" as simple as defining a TLV with values {0x0011, 0x000c, "afritz@iname.com"}. (The type 0x0011 is used throughout the authorization process as the "email address type".) A side note about strings: strings in this protocol are never NULL-terminated. If they look like they are, that's probably a word-length value behind it.

 


Adam Fritzler
Last modified: Fri Jul 24 23:21:53 MST 1998