diff --git a/LICENSE b/LICENSE
new file mode 100644
--- /dev/null
+++ b/LICENSE
@@ -0,0 +1,24 @@
+This is free and unencumbered software released into the public domain.
+
+Anyone is free to copy, modify, publish, use, compile, sell, or
+distribute this software, either in source code form or as a compiled
+binary, for any purpose, commercial or non-commercial, and by any
+means.
+
+In jurisdictions that recognize copyright laws, the author or authors
+of this software dedicate any and all copyright interest in the
+software to the public domain. We make this dedication for the benefit
+of the public at large and to the detriment of our heirs and
+successors. We intend this dedication to be an overt act of
+relinquishment in perpetuity of all present and future rights to this
+software under copyright law.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
+OTHER DEALINGS IN THE SOFTWARE.
+
+For more information, please refer to <http://unlicense.org/>
diff --git a/Setup.hs b/Setup.hs
new file mode 100644
--- /dev/null
+++ b/Setup.hs
@@ -0,0 +1,2 @@
+import Distribution.Simple
+main = defaultMain
diff --git a/diff-gestalt.cabal b/diff-gestalt.cabal
new file mode 100644
--- /dev/null
+++ b/diff-gestalt.cabal
@@ -0,0 +1,37 @@
+name:                diff-gestalt
+version:             0.1.0.0
+synopsis:            A diff algorithm based on recursive longest common substrings
+description:         Please see README.md
+homepage:            http://github.com/chrismwendt/diff-gestalt
+license:             OtherLicense
+license-file:        LICENSE
+author:              Chris Wendt
+maintainer:          chrismwendt@gmail.com
+copyright:           none
+category:            none
+build-type:          Simple
+cabal-version:       >=1.10
+
+library
+  hs-source-dirs:      src
+  exposed-modules:     Data.Algorithm.Diff.Gestalt
+  build-depends:       base >= 4 && < 5
+                     , Diff
+                     , string-similarity
+                     , KMP
+                     , QuickCheck
+  default-language:    Haskell2010
+
+test-suite diff-gestalt-test
+  type:                exitcode-stdio-1.0
+  hs-source-dirs:      test
+  main-is:             Spec.hs
+  build-depends:       base
+                     , Diff
+                     , diff-gestalt
+  ghc-options:         -threaded -rtsopts -with-rtsopts=-N
+  default-language:    Haskell2010
+
+source-repository head
+  type:     git
+  location: https://github.com/chrismwendt/diff-gestalt
diff --git a/src/Data/Algorithm/Diff/Gestalt.hs b/src/Data/Algorithm/Diff/Gestalt.hs
new file mode 100644
--- /dev/null
+++ b/src/Data/Algorithm/Diff/Gestalt.hs
@@ -0,0 +1,23 @@
+module Data.Algorithm.Diff.Gestalt
+    ( diff
+    ) where
+
+import Data.Algorithm.Diff (Diff(..), getGroupedDiff)
+import Data.List.CommonSubstring
+import Data.Algorithms.KMP
+
+split :: Eq a => [a] -> [a] -> ([a], [a])
+split needle haystack = let index = head $ match (build needle) haystack
+                            (left, _) = splitAt index haystack
+                            (_ , right) = splitAt (index + length needle) haystack
+                        in (left, right)
+
+diff :: Ord a => [a] -> [a] -> [Diff [a]]
+diff [] [] = []
+diff as [] = [First as]
+diff [] bs = [Second bs]
+diff as bs = case longestSubstring as bs of
+  [] -> [First as, Second bs]
+  string -> let (las, ras) = split string as
+                (lbs, rbs) = split string bs
+            in diff las lbs ++ [Both string string] ++ diff ras rbs
diff --git a/test/Spec.hs b/test/Spec.hs
new file mode 100644
--- /dev/null
+++ b/test/Spec.hs
@@ -0,0 +1,8 @@
+import System.Exit (exitFailure)
+import Data.Algorithm.Diff.Gestalt
+import Data.Algorithm.Diff (Diff(..))
+
+main :: IO ()
+main = if diff "diff" "riffs" == [First "d", Second "r", Both "iff" "iff", Second "s"]
+  then return ()
+  else exitFailure
