Compiled by Arjun Roychowdhury and Henning Schulzrinne.
Not up-to-date; use current Internet draft instead for definitive reference. Better tools are now available, such as abnf2html. Volunteers to convert the RFC 3261 grammar are solicited.
Based on RFC 2543,RFC 2327, RFC 2616, RFC 1123, RFC 2234, and RFC 2396, Sip Notes and Clarifications.
SIP-message | = | Request | Response | |
Request | = | Request-Line *( general-header | request-header | entity-header ) double-return [message-body] |
; Note - each header ends with a
return and the end of headers is a double return. For
line folding, the folded header must begin with 1*( SP | HT )
|
message-body | = | // Note: This is typically SDP | |
Request-Line | = | Method SP Request-URI SP SIP-Version return | |
SIP-URL | = | "sip:" [userinfo "@" ] hostport url-parameters [ headers] | |
userinfo | = | user [ ":" password ] | |
user | = | *( unreserved | escaped | "&" | "=" | "+" | "$" | "," ) | |
password | = | *( unreserved | escaped | "&" | "=" | "+" | "$" | "," ) | |
hostport | = | host [ ":" port ] | |
host | = | hostname | IPv4address | |
hostname | = | *(domainlabel "." ) toplabel [ "." ] | |
domainlabel | = | alphanum | alphanum *( alphanum | "-" ) alphanum | |
toplabel | = | alpha | alpha *( alphanum | "-" ) alphanum | |
IPv4address | = | 1*digit "." 1*digit "." 1*digit "." 1*digit | |
port | = | * digit | ; empty port field is allowed |
url-parameters | = | *( ";" url-parameter ) | |
url-parameter | = | transport-param | user-param | method-param| ttl-param | maddr-param | other-param | |
transport-param | = | "transport=" ( "udp" | "tcp" ) | |
ttl-param | = | "ttl=" ttl | |
ttl | = | 1*3 DIGIT | ; 0 to 255 |
maddr-param | = | "maddr=" host | |
user-param | = | "user=" ( "phone" | "ip" ) | |
method-param | = | "method=" Method | |
tag-param | = | "tag=" UUID | |
UUID | = | 1*( hex | "-" ) | |
other-param | = | ( token | ( token "=" ( token | quoted-string ))) | |
headers | = | "?"header *( "&" header ) | |
header | = | hname "=" hvalue | |
hname | = | 1*uric | |
hvalue | = | *uric | |
uric | = | reserved | unreserved | escaped | |
reserved | = | ";" | "/" | "?" | ":" | "@" | "&" | "=" | "+" | "$" | "," | |
digits | = | 1*DIGIT | |
telephone-subscriber | = | global-phone-number | local-phone-number | |
global-phone-number | = | "+" 1*phonedigit [isdn-subaddress] [post-dial] | |
local-phone-number | = | 1*(phonedigit | dtmf-digit | pause-character) [isdn-subaddress] [post-dial] | |
isdn-subaddress | = | ";isub=" 1*phonedigit | |
post-dial | = | ";postd=" 1*(phonedigit | dtmf-digit | pause-character) | |
phonedigit | = | DIGIT | visual-separator | |
visual-separator | = | "-" | "." | |
pause-character | = | one-second-pause | wait-for-dial-tone | |
one-second-pause | = | "p" | |
wait-for-dial-tone | = | "w" | |
dtmf-digit | = | "*" | "#" | "A" | "B" | "C" | "D" | |
general-header | = | Accept | Accept-Encoding | Accept-Language | Call-ID | Contact | CSeq | Date | Encryption | Expires | From | Record-Route | Timestamp | To | Via |
|
entity-header | = | Content-Encoding | Content-Length | Content-Type |
|
request-header | = | Authorization |
|
response-header | = | Allow | Authorization | Proxy-Authenticate | Retry-After | Server | Unsupported | Warning | WWW-Authenticate |
|
Method | = | "INVITE" | "ACK" | "OPTIONS" | "BYE" | "CANCEL" | "REGISTER" | |
Accept | = | "Accept" ":" #( media-range [ accept-params ] ) | |
media-range | = | ( "*/*" | ( type "/" "*" ) | ( type "/" subtype ) ) *( ";" parameter ) | |
parameter | = | attribute "=" value | |
attribute | = | token | |
value | = | token | quoted-string | |
accept-params | = | ";" "q" "=" qvalue *( accept-extension ) | |
accept-extension | = | ";" token [ "=" (token | quoted-string ) ] | |
Accept-Encoding | = | "Accept-Encoding" ":" 1#( content-coding ) | |
codings | = | ( content-coding | "*" ) | |
content-coding | = | token | |
Accept-Language | = | "Accept-Language" ":" 1#( language-range [ ";" "q" "=" qvalue ] ) | |
language-range | = | ( ( 1*8ALPHA *( "-" 1*8ALPHA ) ) | "*" ) | |
Proxy-Authorization | = | "Proxy-Authorization" ":" credentials | |
Proxy-Authenticate | = | "Proxy-Authenticate" ":" 1#challenge | |
User-Agent | = | "User-Agent" ":" 1*( product | comment ) | |
Server | = | "Server" ":" 1*( product | comment ) | |
Response | = | Status-Line *( general-header | response-header | entity-header ) double-return [ message-body ] | ; Note - each header ends with a return and the end of headers is a double return. For line folding, the folded header must begin with 1*( SP | HT ) |
Status-Line | = | SIP-version SP Status-Code SP Reason-Phrase | |
SIP-version | = | "SIP/2.0" | |
Status-Code | = | Informational | Success | Redirection | Client-Error | Server-Error | Global-Failure | extension-code |
|
extension-code | = | 3 DIGIT | |
Reason-Phrase | = | *<TEXT-UTF8, excluding CR, LF > | |
Informational | = | "100" | Trying |
| | "180" | ; Ringing | |
| | "181" | ; Call Is Being Forwarded | |
| | "182" | ; Queued | |
Success | = | "200" | ; OK |
Redirection | = | "300" | ; Multiple Choices |
| | "301" | ; Moved Permanently | |
| | "302" | ; Moved Temporarily | |
| | "303" | ; See Other | |
| | "305" | ; Use Proxy | |
| | "380" | ; Alternative Service | |
Client-Error | = | "400" | ; Bad Request |
| | "401" | ; Unauthorized | |
| | "402" | ; Payment Required | |
| | "403" | ; Forbidden | |
| | "404" | ; Not Found | |
| | "405" | ; Method Not Allowed | |
| | "406" | ; Not Acceptable | |
| | "407" | ; Proxy Authentication Required | |
| | "408" | ; Request Timeout | |
| | "409" | ; Conflict | |
| | "410" | ; Gone | |
| | "411" | ; Length Required | |
| | "413" | ; Request Entity Too Large | |
| | "414" | ; Request-URI Too Large | |
| | "415" | ; Unsupported Media Type | |
| | "420" | ; Bad Extension | |
| | "480" | ; Temporarily not available | |
| | "481" | ; Call Leg/Transaction Does Not Exist | |
| | "482" | ; Loop Detected | |
| | "483" | ; Too Many Hops | |
| | "484" | ; Address Incomplete | |
| | "485" | ; Ambiguous | |
| | "486" | ; Busy Here | |
Server-Error | = | "500" | ; Internal Server Error |
| | "501" | ; Not Implemented | |
| | "502" | ; Bad Gateway | |
| | "503" | ; Service Unavailable | |
| | "504" | ; Gateway Time-out | |
| | "505" | ; SIP Version not supported | |
Global-Failure | = | "600" | ; Busy Everywhere |
| | "603" | ; Decline | |
| | "604" | ; Does not exist anywhere | |
| | "606" | ; Not Acceptable | |
message-header | = | field-name ":" [ field-value ] CRLF | |
field-name | = | token | |
field-value | = | *(field-content | LWS ) | |
field-content | = | <the OCTETs making up the field-value and consisting of either *TEXT-UTF8 or combinations of token, separators, and quoted-string > | |
Allow | = | "Allow" ":" 1#Method | |
Call-ID | = | ( "Call-ID" | "i" ) ":" token | |
local-id | = | 1*uric | |
Contact | = | ( "Contact" | "m" ) ":" ("*" | (1# ((name-addr | addr-spec ) [ *( ";" contact-params ) ] [ comment ] ))) | |
name-addr | = | [ display-name ] "<" addr-spec ">" | |
addr-spec | = | SIP-URL | URI | |
display-name | = | *token | quoted-string | |
contact-params | = | "q" "=" qvalue| ("action" "=" "proxy" | "redirect") |( "expires" "=" delta-seconds | <"> SIP-date <">) | extension-attribute | |
extension-attribute | = | extension-name [ "=" extension-value ] | |
Content-Encoding | = | ( "Content-Encoding" | "e" ) ":" 1#content-coding | |
Content-Length | = | ( "Content-Length" | "l" ) ":" 1*DIGIT | |
Content-Type | = | ( "Content-Type" | "c" ) ":"media-type | |
media-type | = | type "/"subtype *( ";" parameter ) | |
type | = | token | |
subtype | = | token | |
CSeq | = | "CSeq" ":" 1*DIGIT Method | |
Date | = | "Date:" SIP-date | |
SIP-date | = | rfc1123-date | |
Encryption | = | "Encryption" ":"encryption-scheme 1*SP #encryption-params | |
encryption-scheme | = | token | |
encryption-params | = | token "=" ( token | quoted-string ) | |
Expires | = | "Expires" ":" ( SIP-date | delta-seconds ) | |
From | = | ( "From" | "f" ) ":" ( name-addr | addr-spec ) *( ";" addr-params ) *(";" extension-params) | |
addr-params | = | tag-param | |
tag-param | = | "tag="UUID | |
Hide | = | "Hide" ":" ( "route" | "hop" ) | |
Max-Forwards | = | "Max-Forwards" ":" 1*DIGIT | |
Organization | = | "Organization" ":" *TEXT-UTF8 | |
Priority | = | "Priority" ":"priority-value | |
priority-value | = | "emergency" | "urgent" | "normal" | "non-urgent" | |
Record-Route | = | "Record-Route" ":" 1# name-addr | |
Require | = | "Require" ":" 1#option-tag | |
Proxy-Require | = | "Proxy-Require" ":" 1#option-tag | |
option-tag | = | token | |
Response-Key | = | "Response-Key" ":" key-scheme 1*SP #key-param | |
key-scheme | = | token | |
key-param | = | token "=" ( token | quoted-string ) | |
Retry-After | = | "Retry-After" ":"( SIP-date | delta-seconds ) [ comment ] [ ";" "duration" "=" delta-seconds ] | |
Route | = | "Route" ":" 1#name-addr | |
Subject | = | ( "Subject" | "s" ) ":" *TEXT-UTF8 | |
Timestamp | = | "Timestamp" ":" *(DIGIT) [ "." *(DIGIT) ] [ delay ] | |
delay | = | *(DIGIT) [ "." *(DIGIT) ] | |
To | = | ( "To" | "t" ) ":" (name-addr | addr-spec ) *( ";" addr-params ) *(";" extension-params) | // Extension params are allowed in From to and Via |
Unsupported | = | "Unsupported" ":" 1#option-tag | |
Via | = | ( "Via" | "v") ":" 1#(sent-protocol sent-by *( ";" via-params ) [ comment ] ) *(";" extension-params) | // Extension params are allowed in From to and Via |
via-params | = | via-hidden | via-ttl | via-maddr| via-received | via-branch | |
via-hidden | = | "hidden" | |
via-ttl | = | "ttl" "=" ttl | |
via-maddr | = | "maddr" "=" maddr | // Note: maddr not defined but it should be host |
via-received | = | "received" "="host | |
via-branch | = | "branch" "=" token | |
sent-protocol | = | protocol-name "/" protocol-version "/" transport | |
protocol-name | = | "SIP" | token | |
protocol-version | = | token | |
transport | = | "UDP" | "TCP" | token | |
sent-by | = | (host [ ":" port ] ) | ( concealed-host ) | |
concealed-host | = | token | |
Warning | = | "Warning" ":" 1#warning-value | |
warning-value | = | warn-code SP warn-agent SP warn-text | |
warn-code | = | 3 DIGIT | |
warn-agent | = | (host [ ":" port ] ) | pseudonym | ; the name or pseudonym of the server adding the Warning header, for use in debugging |
pseudonym | = | token | |
warn-text | = | quoted-string | |
WWW-Authenticate | = | "WWW-Authenticate" ":" 1#challenge | |
auth-scheme | = | token | |
challenge | = | auth-scheme 1*SP realm *("," auth-param) | |
realm | = | "realm" "=" realm-value | |
auth-param | = | token "=" string | |
credentials | = | basic-credentials | (auth-scheme #(auth-params)) | |
basic-credentials | = | "Basic" SP basic-cookie | |
basic-cookie | = | <encrypted string> | |
pgp-challenge | = | * (pgp-params ) | |
pgp-params | = | realm | pgp-version | pgp-algorithm | nonce | |
realm | = | "realm" "="realm-value | |
realm-value | = | quoted-string | |
pgp-version | = | "version" "=" <"> digit *( "." digit ) *letter <"> | |
pgp-algorithm | = | "algorithm" "=" ( "md5" | "sha1" |token ) | |
nonce | = | "nonce" "=" nonce-value | |
nonce-value | = | quoted-string | |
Authorization | = | "Authorization" ":" credentials | |
pgp-response | = | realm | pgp-version | pgp-signature| signed-by | nonce | |
pgp-signature | = | "signature" "="quoted-string | |
signed-by | = | "signed-by" "=" <"> URI <"> | |
pgp-eparams | = | 1# ( pgp-version | pgp-encoding| pgp-key ) | |
pgp-encoding | = | "encoding" "=" "ascii" | token | |
pgp-key | = | "key" "=" quoted-string | |
OCTET | = | %x00-ff | ; any 8-bit sequence of data |
CHAR | = | %x00-7f | ; any US-ASCII character (octets 0 - 127) |
upalpha | = | "A" | "B" | "C" | "D" | "E" | "F" | "G" | "H" | "I" | "J" | "K" | "L" | "M" | "N" | "O" | "P" | "Q" | "R" | "S" | "T" | "U" | "V" | "W" | "X" | "Y" | "Z" | |
lowalpha | = | "a" | "b" | "c" | "d" | "e" | "f" | "g" | "h" | "i" | "j" | "k" | "l" | "m" | "n" | "o" | "p" | "q" | "r" | "s" | "t" | "u" | "v" | "w" | "x" | "y" | "z" | |
alpha | = | lowalpha | upalpha | |
digit | = | "0" | "1" | "2" | "3" | "4" | "5" | "6" | "7" | "8" | "9" | |
alphanum | = | alpha | digit | |
CTL | = | %x00-1f | 0x7f | ; any US-ASCII control character (octets 0 -- 31) and DEL (127) |
CR | = | %d13 | ; US-ASCII CR, carriage return character |
LF | = | %d10 | ; US-ASCII LF, line feed character |
SP | = | %d32 | ; US-ASCII SP, space character |
HT | = | %d09 | ; US-ASCII HT, horizontal tab character |
return | = | CR | LF | CRLF | ; typically the end of a line |
unreserved | = | alphanum | mark | |
double-return | = | (CR CR) | (LF LF) | (CR LF CR LF) | |
mark | = | "-" | "_" | "." | "!" | "~" | "*" | " ' " | "(" | ")" | |
escaped | = | "%"hex hex | |
LWS | = | [CRLF] 1*( SP | HT ) | ; linear whitespace |
TEXT-UTF8 | = | <any UTF-8 character encoding, except CTLs, but including LWS | |
hex | = | "A" | "B" | "C" | "D" | "E" | "F" | "a" | "b" | "c" | "d" | "e" | "f" | digit | |
token | = | 1* (alphanum | "-" | "." | "$" | "%" | "*" | "_" | "+" | "~" | "`" | "'") | |
separators | = | "(" | ")" | "<" | "" | "@" | "," | ";" | ":" | "\" | "<" | "/" | "[" | "]" | "?" | "=" | "{" | "}" | SP | HT | |
comment | = | "(" *(ctext| quoted-pair | comment) ")" | |
ctext | = | <anyTEXT-UTF8 excluding "(" and ")" > | |
quoted-string | = | ( <"> *(qdtext | quoted-pair ) <"> ) | |
qdtext | = | <anyTEXT-UTF8 except <"> > | |
quoted-pair | = | "\"CHAR | |
delta-seconds | = | 1*DIGIT | // This is not spec. in 2543 and no reference is given (its in H.3.3.2) |
qvalue | = | ( "0" [ "." 0*3 DIGIT ] ) | ( "1" [ "." 0*3("0") ] ) | |
URI-reference | = | ([ absoluteURI | relativeURI] [ "#" fragment] ) | (sip-url ) | // According to 2453:4.3 - ReqURI is SIPUri (without certain tokens) or GeneralURI |
absoluteURI | = | scheme":" ( hier_part | opaque_part ) | |
relativeURI | = | (net_path | abs_path | rel_path ) [ "?" query ] | |
hier_part | = | ( net_path | abs_path ) [ "?" query ] | |
opaque_part | = | uric_no_slash *uric | |
uric_no_slash | = | unreserved | escaped | ";" | "?" | ":" | "@" | "&" | "=" | "+" | "$" | "," | |
net_path | = | "//"authority [ abs_path ] | |
abs_path | = | "/"path_segments | |
rel_path | = | rel_segment [ abs_path ] | |
rel_segment | = | 1*(unreserved | escaped | ";" | "@" | "&" | "=" | "+" | "$" | "," ) | |
scheme | = | alpha *( alpha | digit | "+" | "-" | "." ) | |
authority | = | server_H | reg_name | |
reg_name | = | 1*( unreserved | escaped | "$" | "," | ";" | ":" | "@" | "&" | "=" | "+" ) | |
server_H | = | [ [ userinfo_H "@" ] hostport ] | |
userinfo_H | = | *( unreserved | escaped | ";" | ":" | "&" | "=" | "+" | "$" | "," ) | |
path | = | [ abs_path | opaque_part ] | |
path_segments | = | segment *( "/" segment ) | |
segment | = | *pchar *( ";" param ) | |
param | = | *pchar | |
pchar | = | unreserved | escaped | ":" | "@" | "&" | "=" | "+" | "$" | "," | |
query | = | *uric | |
fragment | = | *uric | |
product | = | token ["/" product-version] | |
product-version | = | token | |
rfc1123-date | = | wkday "," SP date1SP time SP "GMT" | |
date1 | = | 2DIGIT SP month SP 4DIGIT | ; day month year (e.g., 02 Jun 1982) |
time | = | 2 DIGIT ":" 2 DIGIT ":" 2DIGIT | ; 00:00:00 - 23:59:59 |
wkday | = | "Mon" | "Tue" | "Wed"| "Thu" | "Fri" | "Sat" | "Sun" | |
month | = | "Jan" | "Feb" | "Mar" | "Apr" | "May" | "Jun" | "Jul" | "Aug" | "Sep" | "Oct" | "Nov" | "Dec" | |
announcement | = | proto-version origin-field session-name-field information-field uri-field email-fields phone-fields connection-field bandwidth-fields time-fields key-field attribute-fields media-descriptions |
|
proto-version |
= | "v=" 1*DIGIT return | ;this memo describes version 0 |
origin-field | = | "o=" username space sess-id space sess-version space nettype space addrtype space addr return |
|
session-name-field |
= | "s=" text return | |
information-field |
= | ["i=" text return] | |
uri-field | = | ["u=" uri return] | |
email-fields |
= | *("e=" email-address return) | |
phone-fields |
= | *("p=" phone-number return) | |
connection-field
|
= | ["c=" nettype space addrtype space connection-address return] |
;a connection field must be present ;in every media description or at the ;session-level |
bandwidth-fields |
= | *("b=" bwtype ":" bandwidth return) | |
time-fields |
= | 1*( "t=" start-time space stop-time *(return repeat-fields) return) [zone-adjustments return] |
|
repeat-fields |
= | "r=" repeat-interval space typed-time 1*(space typed-time) |
|
zone-adjustments
|
= | time space
["-"] typed-time *(space time space ["-"] typed-time) |
|
key-field |
= | ["k=" key-type return] | |
key-type |
= | "prompt" | "clear:" key-data | "base64:" key-data |"uri:" uri | |
key-data |
= | email-safe | "~" | " | |
attribute-fields | = | *("a=" attribute return) | |
media-field | = | "m=" media space
port ["/" integer] space proto 1*(space fmt) return |
|
media-descriptions
|
= | *( media-field information-field *(connection-field) bandwidth-fields key-field attribute-fields ) |
|
media | = | 1*(alpha-numeric) | ;typically "audio", "video",
"application" ;or "data" |
fmt |
= | 1*(alpha-numeric) | ;typically an RTP payload type for audio ;and video media |
proto |
= | 1*(alpha-numeric) | ;typically "RTP/AVP" or "udp" for IP4 |
port |
= | 1*(DIGIT) | ;should in the range "1024" to "65535"
inclusive ;for UDP based media |
attribute |
= | (att-field ":" att-value) | att-field | |
att-field |
= | 1*(alpha-numeric) | |
att-value |
= | byte-string | |
sess-id |
= | 1*(DIGIT) | ;should be unique for this originating username/host |
sess-version |
= | 1*(DIGIT) | ;0 is a new session |
connection-address
|
= | multicast-address | addr |
|
multicast-address
|
= | 3*(decimal-uchar ".") decimal-uchar
"/" ttl [ "/" integer ] |
;multicast addresses may be in the range ;224.0.0.0 to 239.255.255.255 |
start-time | = | time | "0" | |
stop-time | = | time | "0" | |
time | = | POS-DIGIT 9*(DIGIT) | ;sufficient for 2 more centuries |
repeat-interval
|
= | typed-time | |
typed-time |
= | 1*(DIGIT) [fixed-len-time-unit] | |
fixed-len-time-unit | = | "d" | "h" | "m" | "s" | |
bwtype |
= | 1*(alpha-numeric) | |
bandwidth |
= | 1*(DIGIT) | |
username |
= | safe | ;pretty wide definition, but doesn't include space |
email-address |
= | email | email
"(" email-safe ")" | email-safe "<" email ">" |
|
email |
= | ; defined in RFC822 | |
phone-number |
= | phone | phone
"(" email-safe ")" | email-safe "<" phone ">" |
|
phone |
= | "+" POS-DIGIT 1*(space | "-" | DIGIT) | ;there must be a space or hyphen between the ;international code and the rest of the number. |
nettype | = | "IN" | ;list to be extended |
addrtype | = | "IP4" | "IP6" | ;list to be extended |
addr |
= | FQDN | unicast-address | |
FQDN |
= | 4*(alpha-numeric|"-"|".") | ;fully qualified domain name as specified in RFC1035 |
unicast-address
|
= | IP4-address | IP6-address | |
IP4-address |
= | b1 "." decimal-uchar "." decimal-uchar "." b4 | |
b1 |
= | decimal-uchar | ;less than "224"; not "0" or "127" |
b4 |
= | decimal-uchar | ;not "0" |
IP6-address |
= | ;to be defined | |
text |
= | byte-string | ;default is to interpret this as I0-10646 UTF8 ;ISO 8859-1 requires a "a=charset:ISO-8859-1" ;session-level attribute to be used |
byte-string |
= | 1*(0x01..0x09|0x0b|0x0c|0x0e..0xff) | ;any byte except NUL, CR or LF |
decimal-uchar | = | DIGIT | POS-DIGIT DIGIT | ("1" 2*(DIGIT)) | ("2" ("0"|"1"|"2"|"3"|"4") DIGIT) | ("2" "5" ("0"|"1"|"2"|"3"|"4"|"5")) |
|
integer |
= | POS-DIGIT *(DIGIT) | |
POS-DIGIT |
= | "1"|"2"|"3"|"4"|"5"|"6"|"7"|"8"|"9" | |
email-safe |
= | safe | space | tab | |
safe |
= | alpha-numeric | "'" | "'" | "-" | "." | "/" | ":" | "?" | """ | "#" | "$" | "&" | "*" | ";" | "=" | "@" | "[" | "]" | "^" | "_" | "`" | "{" | "|" | "}" | "+" | "~" | " |
|
space | = | SP |
Last updated by Henning Schulzrinne