             [cljs.source-map.base64-vlq :as base64-vlq]))
 
 ;; =============================================================================
-;; All source map code in the file assumes the following in memory
+;; Source map code in the file assumes the following in memory
+;; representation of source map data.
+;;
+;; { gline[Integer]
+;;   { gcol[Integer]
+;;    [{ :line ..., :col ..., :name ..., :source ... }] } }
+;;
+;; Reverse source map code in the file assumes the following in memory
 ;; representation of source map data.
 ;;
 ;; { file-name[String]
 ;;   { line[Integer]
 ;;     { col[Integer]
-;;       [{ :gline ..., :gcol ..., :name ...}] } }
-;;
-;; The outer level is a sorted map where the entries are file name and
-;; sorted map of line information, the keys are strings. The line
-;; information is represented as a sorted map of of column
-;; information, the keys are integers. The column information is a
-;; sorted map where the keys are integers and values are a vector of
-;; maps - these maps have the keys :gline and :gcol for the generated
-;; line and column.  A :name key may be present if available.
-;;
-;; This representation simplifies merging ClojureScript source map
-;; information with source map information generated by Google Closure
-;; Compiler optimization. We can now trivially create the merged map
-;; by using :gline and :gcol in the ClojureScript source map data to
-;; extract final :gline and :gcol from the Google Closure source map.
+;;       [{ :gline ..., :gcol ..., :name ... }] } }
 
 ;; -----------------------------------------------------------------------------
 ;; Utilities
 
 (defn indexed-sources
   "Take a seq of source file names and return a map from
-   file number to integer index."
+   file number to integer index. For reverse source maps."
   [sources]
   (->> sources
     (map-indexed (fn [a b] [a b]))

      (with-meta nseg {:name (+ name rname)})
      nseg)))

(defn update-result
  "Helper for decode. Take an internal source map representation
   organized as nested sorted maps mapping file, line, and column
   and update it based on a segment map and generated line number."
  [result segmap gline]
  (let [{:keys [gcol source line col name]} segmap
        d {:gline gline

                         (let [seg (first segs)
                               nrelseg (seg-combine (base64-vlq/decode seg) relseg)]
                           (recur (next segs) nrelseg
                             (update-reverse-result result (seg->map nrelseg source-map) gline)))
                         [result relseg]))))]
             (recur (inc gline) (next lines) (assoc relseg 0 0) result))
           result)))))

(defn update-result
  "Helper for decode. Take a source map and update it based on a
  segment map."
  [result segmap gline]
  (let [{:keys [gcol source line col name]} segmap
        d {:line col
           :col  line
           :source source}
        d (if name (assoc d :name name) d)]
    (update-in result [gline]
      (fnil (fn [m]
              (update-in m [gcol]
                (fnil #(conj % d) [])))
            (sorted-map)))))

(defn decode
  "Convert a v3 source map JSON object into a source map mapping
  generated JavaScript source locations to the original
  ClojureScript."
  ([source-map]
     (decode (aget source-map "mappings") source-map))
  ([mappings source-map]
     (let [sources (aget source-map "sources")
           relseg-init [0 0 0 0 0]
           lines (seq (string/split mappings #";"))]
       (loop [gline 0 lines lines relseg relseg-init result {}]
         (if lines
           (let [line (first lines)
                 [result relseg]
                 (if (string/blank? line)
                   [result relseg]
                   (let [segs (seq (string/split line #","))]
                     (loop [segs segs relseg relseg result result]
                       (if segs
                         (let [seg (first segs)
                               nrelseg (seg-combine (base64-vlq/decode seg) relseg)]
                           (recur (next segs) nrelseg
                             (update-result result (seg->map nrelseg source-map) gline)))
                         [result relseg]))))]
             (recur (inc gline) (next lines) (assoc relseg 0 0) result))
