diff -ur mtr-0.80/curses.c mtr-0.80-patched/curses.c
--- mtr-0.80/curses.c	2008-10-10 14:51:25.000000000 -0400
+++ mtr-0.80-patched/curses.c	2010-08-08 20:58:33.000000000 -0400
@@ -288,6 +288,7 @@
 {
   int max;
   int at;
+  struct mplslen *mpls, *mplss;
   ip_t *addr, *addrs;
   int y, x;
   char *name;
@@ -301,6 +302,7 @@
   for(at = net_min () + display_offset; at < max; at++) {
     printw("%2d. ", at + 1);
     addr = net_addr(at);
+    mpls = net_mpls(at);
 
     if( addrcmp( (void *) addr, (void *) &unspec_addr, af ) != 0 ) {
       name = dns_lookup(addr);
@@ -310,7 +312,7 @@
 	printw("%s", name);
       } else {
 	printw("%s", strlongip( addr ) );
-      }
+      } 
       attroff(A_BOLD);
 
       getyx(stdscr, y, x);
@@ -339,9 +341,14 @@
       buf[hd_len] = 0;
       printw("%s", buf);
 
+      if (mpls->inclabel) {
+     printw("     [MPLS: Lbl %lu Exp %u S %d]", mpls->label, mpls->exp, mpls->s);
+      }
+
       /* Multi path by Min */
       for (i=0; i < MAXPATH; i++ ) {
         addrs = net_addrs(at, i);
+        mplss = net_mplss(at, i);
 	if ( addrcmp( (void *) addrs, (void *) addr, af ) == 0 ) continue;
 	if ( addrcmp( (void *) addrs, (void *) &unspec_addr, af ) == 0 ) break;
 
@@ -352,6 +359,9 @@
         } else {
 	  printw("\n    %s", strlongip( addrs ) );
         }
+        if (mpls->inclabel) {
+       printw("\n    [MPLS: Lbl %lu Exp %u S %d]", mplss->label, mplss->exp, mplss->s);
+        }
         attroff(A_BOLD);
       }
 
diff -ur mtr-0.80/net.c mtr-0.80-patched/net.c
--- mtr-0.80/net.c	2010-07-13 02:10:33.000000000 -0400
+++ mtr-0.80-patched/net.c	2010-08-08 20:58:30.000000000 -0400
@@ -122,6 +122,8 @@
   int transit;
   int saved[SAVED_PINGS];
   int saved_seq_offset;
+  struct mplslen mpls;	/* size of ICMP reply */
+  struct mplslen mplss[MAXPATH];
 };
 
 
@@ -434,7 +436,7 @@
 
 /*   We got a return on something we sent out.  Record the address and
      time.  */
-void net_process_ping(int seq, void * addr, struct timeval now) 
+void net_process_ping(int seq, struct mplslen mpls, void * addr, struct timeval now) 
 {
   int index;
   int totusec;
@@ -467,10 +469,12 @@
 		(void *) &unspec_addr, af ) == 0 ) {
     /* should be out of if as addr can change */
     addrcpy( (void *) &(host[index].addr), addrcopy, af );
+    host[index].mpls = mpls;
     display_rawhost(index, (void *) &(host[index].addr));
 
   /* multi paths by Min */
     addrcpy( (void *) &(host[index].addrs[0]), addrcopy, af );
+    host[index].mplss[0] = mpls;
   } else {
     for( i=0; i<MAXPATH; ) {
       if( addrcmp( (void *) &(host[index].addrs[i]), (void *) &addrcopy,
@@ -482,6 +486,7 @@
     if( addrcmp( (void *) &(host[index].addrs[i]), addrcopy, af ) != 0 && 
         i<MAXPATH ) {
       addrcpy( (void *) &(host[index].addrs[i]), addrcopy, af );
+      host[index].mplss[i] = mpls;
       
       /* rafaelmartins: multi path support to '--raw' */
       display_rawhost(index, (void *) &(host[index].addrs[i]));
@@ -563,6 +568,10 @@
   struct timeval now;
   ip_t * fromaddress = NULL;
   int echoreplytype = 0, timeexceededtype = 0, unreachabletype = 0;
+  unsigned int ext_ver, ext_res, ext_chk, obj_hdr_len;
+  u_char obj_hdr_class, obj_hdr_type;
+  struct mplslen mpls;
+  mpls.inclabel = 0;
   int sequence = 0;
 
   gettimeofday(&now, NULL);
@@ -623,6 +632,31 @@
         header = (struct ICMPHeader *)(packet + sizeof (struct IPHeader) + 
                                                 sizeof (struct ICMPHeader) + 
                                                 sizeof (struct IPHeader));
+
+        /* taken with small modifications from the NANOG-modified traceroute.c
+         * credit for the bulk of the decoding goes to Jorge Boncompte */
+        if(num > 160) {
+          ext_ver = packet[156]>>4;
+          ext_res = (packet[156]&15)+ packet[157];
+          ext_chk = ((unsigned int)packet[158]<<8)+packet[159];
+  
+          if (ext_ver == 2 && ext_res == 0 && ext_chk != 0) {
+          /* Ok. This is an ICMP ext header. But we haven't checked
+            that the checksum is correct */ 
+            obj_hdr_len = ((int)packet[160]<<8)+packet[161];
+            obj_hdr_class = packet[162];
+            obj_hdr_type = packet[163];
+  
+            if (obj_hdr_len >= 8 && obj_hdr_class == 1 && obj_hdr_type == 1) {
+              mpls.label = ((unsigned long)packet[164]<<12) +
+                  ((unsigned int)packet[165]<<4) + ((packet[166]>>4) & 0xff); 
+              mpls.exp = (packet[166]>>1) & 0x7;
+              mpls.s = (packet[166] & 0x1);	/* bottom of stack bit */
+              mpls.inclabel = 1;
+            }
+          }
+        }
+
       break;
 #ifdef ENABLE_IPV6
       case AF_INET6:
@@ -674,7 +708,7 @@
   }
 
   if (sequence)
-    net_process_ping(sequence, (void *)fromaddress, now);
+    net_process_ping (header->sequence, mpls, (void *) fromaddress, now);
 }
 
 
@@ -689,6 +723,15 @@
   return (ip_t *)&(host[at].addrs[i]);
 }
 
+void *net_mpls(int at)
+{
+  return (struct mplslen *)&(host[at].mplss);
+}
+
+void *net_mplss(int at, int i)
+{
+  return (struct mplslen *)&(host[at].mplss[i]);
+}
 
 int net_loss(int at) 
 {
diff -ur mtr-0.80/net.h mtr-0.80-patched/net.h
--- mtr-0.80/net.h	2008-10-10 14:50:04.000000000 -0400
+++ mtr-0.80-patched/net.h	2010-08-08 19:38:32.000000000 -0400
@@ -40,6 +40,8 @@
 int net_min(void);
 int net_last(int at);
 ip_t * net_addr(int at);
+void * net_mpls(int at);
+void * net_mplss(int, int);
 int net_loss(int at);
 int net_drop(int at);
 int net_last(int at);
@@ -119,3 +121,9 @@
 extern char available_options[];
 
 ip_t unspec_addr;
+
+struct mplslen {
+  unsigned long label;
+  uint8 exp;
+  char s, inclabel;
+};
diff -ur mtr-0.80/report.c mtr-0.80-patched/report.c
--- mtr-0.80/report.c	2010-05-31 11:53:21.000000000 -0400
+++ mtr-0.80-patched/report.c	2010-08-08 18:31:33.000000000 -0400
@@ -53,6 +53,7 @@
 void report_close(void) 
 {
   int i, j, at, max, z, w;
+  struct mplslen *mpls, *mplss;
   ip_t *addr;
   ip_t *addr2 = NULL;  
   char name[81];
@@ -102,6 +103,7 @@
   at  = net_min();
   for(; at < max; at++) {
     addr = net_addr(at);
+    mpls = net_mpls(at);
     if( addrcmp( (void *) addr, (void *) &unspec_addr, af ) == 0 ) {
       sprintf(name, "???");
     } else {
@@ -138,24 +140,41 @@
      * This feature show 'loadbalances' on routes 
      */
     
-   /* z is starting at 1 because addrs[0] is the same that addr */
+    /* z is starting at 1 because addrs[0] is the same that addr */
     for (z = 1; z < MAXPATH ; z++) {
-       addr2 = net_addrs(at, z);
-       int found = 0;
-       if ((addrcmp ((void *) &unspec_addr, (void *) addr2, af)) == 0)
-          break;
+      addr2 = net_addrs(at, z);
+      mplss = net_mplss(at, z);
+      int found = 0;
+      if ((addrcmp ((void *) &unspec_addr, (void *) addr2, af)) == 0)
+        break;
       for (w = 0; w < z; w++)
         /* Thales -- Ok... checking if there are ips repeated on same hop */
-           if ((addrcmp ((void *) addr2, (void *) net_addrs (at,w), af)) == 0) {
-              found = 1;
-              break;
-           }   
-       if (!found) {
-        if (z == 1)  
+        if ((addrcmp ((void *) addr2, (void *) net_addrs (at,w), af)) == 0) {
+           found = 1;
+           break;
+        }   
+
+      if (!found) {
+
+        if (mpls->inclabel && z == 1) {
+          printf("    |  |+-- [MPLS: Lbl %lu Exp %u S %d]\n", mpls->label, mpls->exp, mpls->s);
+        }
+
+        if (z == 1) {
           printf ("    |  `|-- %s\n", strlongip(addr2));
-        else 
+          if (mplss->inclabel)
+            printf("    |   +-- [MPLS: Lbl %lu Exp %u S %d]\n", mplss->label, mplss->exp, mplss->s);
+        } else {
           printf ("    |   |-- %s\n", strlongip(addr2));
-       }
+          if (mplss->inclabel)
+            printf("    |   +-- [MPLS: Lbl %lu Exp %u S %d]\n", mplss->label, mplss->exp, mplss->s);
+        }
+      }
+    }
+
+    /* No multipath */
+    if(mpls->inclabel && z == 1) {
+      printf("    |   +-- [MPLS: Lbl %lu Exp %u S %d]\n", mpls->label, mpls->exp, mpls->s);
     }
   }
 }
