COMMAND

    Novell Netware

SYSTEMS AFFECTED

    Novell Netware 5.0, 5.1 including the latest patches

PROBLEM

    Following  is  based  on  Razor  BindView  Advisory.     Due  to a
    combination of legacy support and default settings, Novell Netware
    servers using native IP will leak system information via TCP  port
    524   when   properly   queried.     In   mixed   Novell/Microsoft
    environments, information  regarding Microsoft  devices is  leaked
    via the  Service Advertising  Protocol (SAP)  table.   Third party
    products, such  as those  used to  synchronize directory  services
    between  environments  can  further  the  problem.  Essentially, a
    remote attacker can gather the equivalent information provided  by
    the console command "display  servers" and the DOS  client command
    "cx /t /a /r" without authentication.

    RAZOR has received reports  of distributed port scans  looking for
    port 524 on the Internet, so this technique is probably being used
    by potential attackers to gain information from potential targets.

    All Novell Netware servers running IP (with port 524 open) can  be
    queried and all objects with Public read access can be enumerated.
    Information  such  as  account  names,  server services, and other
    various objects can  be gathered. In  mixed environments, such  as
    environments with a mixture of  IPX and IP, some IPX  objects that
    are managed and communicate  with IP-based servers can  be leaked,
    and in  an environment  with Microsoft  NT some  NT objects can be
    leaked.  The information gathered could be used to enumerate  user
    account names and technologies  deployed, which could be  used for
    a future attack.

    The scope of the impact is limited to the internal network  unless
    TCP port 524 access is  allowed through a firewall or  from dialup
    technologies deployed internally.  This  is similar in scope to  a
    Windows  NT  null  session  against  a  Primary  or  Backup Domain
    Controller.

    Novell has pushed to  make its Netware environment  as connectable
    as possible.   To this  end, Novell  has deployed  a "pure" TCP/IP
    environment (as opposed to  previous implementations that did  not
    fully incorporate Netware into the IP world, such as  Netware/IP).
    The assigned port 524 is  for NCP (Netware Core Protocol),  and is
    used in pretty much the same fashion as IPX was previously.   This
    allows normal IPX-based applications  running on the client  to be
    able to communicate with an IP-only Netware server, as the  client
    software "wraps" the IPX request in  an IP packet and sends it  to
    port 524.

    Traditionally in  Netware environments,  IPX was  used exclusively
    for  both  client-to-server  and  server-to-server communications.
    Netware  objects,  such  as  printers,  would  act as clients to a
    server so when the end user wanted to communicate with a  printer,
    he  or  she  could  query  the  server and receive the information
    about the printer's location.  Additionally, Netware servers could
    also route IPX  communications between multiple  network interface
    cards, and learn about other services available on other  servers,
    all  via  IPX.   To  preserve  this  rich environment, most of the
    technologies   involved    were   ported    to   use    IP    with
    backwards-compatibility in mind.  Basically this means that  since
    IP did not support this "auto-discovery" of available services  on
    its own, Novell used a  combination of wrapping NCP commands  (the
    commands   that   used   to    be   sent   client-to-server    and
    server-to-server over IPX) in IP packets over port 524, and  using
    SLP (Service Location Protocol) over port 427.

    Novell has been very good at trying to ensure it does not lock out
    older  versions  of  Netware  with  interoperability  with   newer
    versions.  However because of  this history, older NCP calls  used
    two or three  major versions ago  can still be  used to query  the
    server.  Since these calls can  now be wrapped in IP, we  can make
    the calls from non-Netware systems. And since many of these  calls
    are not dependent upon the user authenticating first, we can  take
    advantage  of  default  NDS  tree  settings  in enumeration of NDS
    objects:

        http://razor.bindview.com/tools/files/ncpquery-1.2.tgz

    1. Build the TCP connection. Send TCP packet with SYN to port 524,
       receive the SYN/ACK, reply with an ACK. Your basic connection.
    2. Now we build the NCP connection.  This is done the same way  as
       IPX, except we are putting the data in a TCP packet.  We  start
       with an  NCP header  with no  NCP data,  using connection  type
       0x1111.

        NCP (create_conn)
        {
                // begin NCP request header
                u32 sig;        // signature identifies the packet type (0x446d6454)
                u32 len;        // length 0x00000017 (23)
                u32 reqbuf;     // requested buffer size 0x00000000
                u16 reqtype;    // request type 0x1111 (create connection)
                u8  seq;        // initial sequence number 0x00
                u8  connlow;    // 0xff (255) wildcard
                u8  task;       // 0x01
                u8  connhi;     // 0xff (255) wildcard
                // end NCP request header
        } create_conn_req;

       And here is the reply:

        NCP (create_conn_reply)
        {
                // begin NCP reply header
                u32 sig;        // signature
                u32 len;        // length 0x00000010 (16)
                u16 reqtype;    // reply 0x3333
                u8  seq;        // initial sequence number 0x00
                u8  connlow;    // 0x0e (14) <--\
                u8  task;       // 0x01          >-- connection number
                u8  connhi;     // 0x00 (0)  <--/
                // end NCP reply header
                // begin data section
                u8  cc;         // completion code 0x00 (OK)
                u8  cs;         // connection status flags 0x00 (OK)
                // end data section
        } create_conn_rep;

       Now we have a connection to the Netware server.
    3. Now  we  do  a  Server  Info  Request  call  to  gather   basic
       information about the server.

        NCP (server info request)
        {
                // begin NCP header
                u32 sig;        // signature (0x446d6454)
                u32 len;        // length = 0x0000001a (26)
                u32 ver;        // version = 0x00000001
                u32 bufreply;   // reply buffer size = 0x00000080 (128)
                u16 reqtype;    // 0x2222 (request)
                u8  seq;        // 0x01 sequence number is incremented by one
                u8  connlow;    // Conn low 0x0e (14)
                u8  task;       // Task # 0x01
                u8  connhi;     // Conn hi 0x00 (0)
                // end NCP header
                // Request/sub-function code = 23,17
                u32 req;        // 0x17000111 (23,0,1,17)
        } server_info_req;

       Note that we incremented the  sequence number by one.   This is
       the  old  IPX  packet  sequence  numbering  scheme, which is to
       increment by one, unless the  number is 255 and then  you reset
       it back to zero.

       In the reply we get back a bunch of information:

        NCP (server info reply)
        {
                // begin NCP header
                u32 sig;        // 4 byte signature
                u32 len;        // length = 0x00000090 (144)
                u16 reqtype;    // 0x3333 (reply)
                u8  seq;        // 0x01 sequence number
                u8  connlow;    // Conn low 0x0e (14)
                u8  task;       // Task # 0x01
                u8  connhi;     // Conn hi 0x00 (0)
                // end NCP header
                // Reply/sub-function code = 23,17
                u8  cc;         // completion code = 0x00 (ok)
                u8  cs;         // connection status flags = 0x00 (ok)
                u8[47] svrname; // object name = 0x50 41 4e (PAN)
                u8  ser_ver;    // file service version = 0x05
                u8  ser_subver; // file service sub-version = 0x00
                u16 max_conn;   // max service connections = 0x000e
                u16 conn_use;   // connections in use = 0x0000
                u16 max_vols;   // maximum volumes = 0x00ff
                u8  rev;        // revision = 0x00
                u8  sft;        // sft level = 0x02
                u8  tts;        // tts level = 0x01
                u16 max_used;   // max conn ever used = 0x01
                u8  acct;       // account version = 0x01
                u8  vap;        // VAP version = 0x01
                u8  queue;      // Queue version = 0x01
                u8  print;      // Print version = 0x00
                u8  virt_con;   // Virtual console version = 0x01
                u8  int_brdg;   // Internet bridge = 0x01
        } server_info_rep;

       Now we know the  server name is PAN,  it is Netware 5.0,  and a
       few other items.

    4. Do an NDS Ping which will  return the NDS Tree name.  NDS  Ping
       is used  to tell  if servers  are up.   Clients typically  send
       these packets  to the  first server  available.   We'll use  it
       because  it  allows  us  to  determine  the  tree  name without
       authenticating.

        NCP (NDS_ping)
        {
                // begin NCP header
                u32 sig;        // signature (0x446d6454)
                u32 len;        // length = 0x0000001b (27)
                u32 ver;        // version = 0x00000001
                u32 bufreply;   // reply buffer size = 0x00000028 (40)
                u16 reqtype;    // 0x2222 (request)
                u8  seq;        // 0x02 sequence number is incremented by one
                u8  connlow;    // Conn low 0x0e (14)
                u8  task;       // Task # 0x01
                u8  connhi;     // Conn hi 0x00 (0)
                // end NCP header
                // Request/sub-function code = 104,0
                u32 req;        // 0x68010000 (104,1,0,0)
        } NDS_ping_req;

       And here's the reply:

        NCP (NDS_ping_reply)
        {
                // begin NCP reply header
                u32 sig;        // signature
                u32 len;        // length 0x00000010 (16)
                u16 reqtype;    // reply 0x3333
                u8  seq;        // 0x02 sequence number
                u8  connlow;    // 0x0e (14) <--\
                u8  task;       // 0x01          >-- connection number
                u8  connhi;     // 0x00 (0)  <--/
                // end NCP reply header
                // begin data section
                u8  cc;         // completion code 0x00 (OK)
                u8  cs;         // connection status flags 0x00 (OK)
                u32 u1;         // unknown
                u32 treelen;    // length of tree name
                u8[21] treename;// 0x54 45 53 54 (in this example, TEST)
                u32 objid;      // object ID of tree
                // end data section
        } NDS_ping_rep;

       Now we have the NDS tree name.
    5. Finally by sending a Scan  Bindery Object request in a loop  we
       can enumerate all objects with at least public read access.

        NCP (scan bindery object request)
        {
                // begin NCP header
                u32 sig;        // signature (0x446d6454)
                u32 len;        // length = 0x00000022 (34)
                u32 ver;        // version = 0x00000001
                u32 bufreply;   // reply buffer size = 0x00000039 (57)
                u16 reqtype;    // 0x2222 (request)
                u8  seq;        // 0x03 (3) sequence number
                u8  connlow;    // Conn low 0x0e (14)
                u8  task;       // Task # 0x01
                u8  connhi;     // Conn hi 0x00 (0)
                // end NCP header
                // Request/sub-function code = 23,55
                u32 req;        // 0x17000837 (23,0,8,55)
                u32 lastobj;    // Last object ID seen = 0xffffffff (wild card)
                                // start with ffffffff and simply use the last
                                // object ID that was retrieved
                u16 objtype;    // Object type = 0xffff (wildcard)
                u16 search;     // search string = 0x012a ("*")
        } scan_bin_obj_req;

       Here is a sample reply:

        NCP (scan bindery object reply)
        {
                // begin NCP header
                u32 sig;        // signature (0x446d6454)
                u32 len;        // length = 0x00000049
                u32 reqtype;    // 0x3333 = (reply)
                u8  seq;        // 0x03 (3) sequence number
                u8  connlow;    // Conn low 0x0e (14)
                u8  task;       // Task # 0x01
                u8  connhi;     // Conn hi 0x00 (0)
                // end NCP header
                u8  cc;         // completion code = 0x00
                u8  cs;         // connection status flags = 0x00
                u32 obj_id;     // object ID found (0xc20000a1)
                u16 objtype;    // object type = 0x0004 (server)
                u8[48] objname; // object name = 0x50 41 4e (PAN)
                u8  objflag;    // object flag = 0x00 (static)
                u8  sec;        // security status = 0x40 (0100 write access for svr,
                                                           0000 read access for all)
                u8  statflags;  // status flags = 0xff (has properties)
        } scan_bin_obj_rep;

    The  interesting  thing  is  that  if  the  NDS  tree object named
    [Public] has  Browse rights,  all objects  except those restricted
    by  Inherited  Rights  Filters  will  have their names enumerated,
    e.g.   user names.   The default  setting for  Novell is  to  have
    Browse rights on [Public].

    In addition to enumeration of NDS objects, all dynamic listings in
    the  SAP  table  will  be  enumerated.   This  includes  not  just
    additional  Novell  services  in  the  environment, such as non-IP
    Novell systems  that the  IP Novell  systems are  talking to,  but
    other vendor software and hardware products as well.  For example,
    SAP  type  0x0640  is  for  NT  RPC  services, 0x64e is for NT IIS
    servers.  Using the information  in the SAP table and  refering to
    a list of Novell-assigned SAP types, various deployed technologies
    can be enumerated as well.

    Microsoft  systems   that  advertise   file  and   print  services
    recognizable by  the Novell  environment can  have their  computer
    Netbios names enumerated via the 0x0640 SAP type.

    While NDS tree browsing can be limited by adjusting default rights
    on the NDS tree, this does  not limit the information that can  be
    leaked via the SAP table.

SOLUTION

    Novell feels  that the  following recommendations  section is fine
    the  way  it  is.   No  patch,  just  configuration  issues.   The
    seriousness can probably best be assessed by running the  NCPQuery
    tool against your Netware servers  that are running IP.   Probably
    the most interesting thing is the tool runs on plain old Unix,  so
    probes from the Internet are possible if port 524 is open.

    Due  to  the  amount  of  information  leaked  via port 524, it is
    recommended that access to port 524 be blocked from the  Internet.
    The NDS object  [Public] should not  have Browse rights,  the tree
    should  be  restricted  to  authenticated  users  only,  so remove
    Browse rights from  [Public].  Use  the ncpquery tool  to check to
    see what is leaking via port 524.  Internal threats may be  harder
    to defend  against, particularly  the information  that leaks  via
    the dynamic SAP  table, but removing  Browse from [Public]  should
    at least limit user name enumeration.