diff --git a/configure.in b/configure.in
index 1271a56..cebe1d2 100644
--- a/configure.in
+++ b/configure.in
@@ -27,8 +27,8 @@ CHECK_ATOMIC_OPS
 
 dnl Checks for header files.
 AC_HEADER_STDC
-AC_CHECK_HEADERS(asm/ptrace_offsets.h endian.h execinfo.h ia64intrin.h \
-		 sys/uc_access.h unistd.h signal.h)
+AC_CHECK_HEADERS(asm/ptrace_offsets.h endian.h machine/endian.h execinfo.h \
+                 ia64intrin.h sys/uc_access.h unistd.h signal.h)
 
 dnl Checks for typedefs, structures, and compiler characteristics.
 AC_C_CONST
@@ -80,6 +80,7 @@ get_arch() {
   hppa*) echo hppa;;
   mips*) echo mips;;
   powerpc*) is_gcc_m64;;
+  amd64*) echo x86_64;;
   *) echo $1;;
  esac
 }
@@ -99,6 +100,7 @@ AM_CONDITIONAL(ARCH_PPC32, test x$target_arch = xppc32)
 AM_CONDITIONAL(ARCH_PPC64, test x$target_arch = xppc64)
 AM_CONDITIONAL(OS_LINUX, expr x$target_os : xlinux >/dev/null)
 AM_CONDITIONAL(OS_HPUX, expr x$target_os : xhpux >/dev/null)
+AM_CONDITIONAL(OS_FREEBSD, expr x$target_os : xfreebsd >/dev/null)
 
 if test x$target_arch = xppc64; then
         libdir='${exec_prefix}/lib64'
diff --git a/include/libunwind-x86_64.h b/include/libunwind-x86_64.h
index e337351..98af8e7 100644
--- a/include/libunwind-x86_64.h
+++ b/include/libunwind-x86_64.h
@@ -33,6 +33,7 @@ extern "C" {
 #endif
 
 #include <inttypes.h>
+#include <sys/types.h>
 #include <ucontext.h>
 
 #define UNW_TARGET		x86_64
diff --git a/include/libunwind_i.h b/include/libunwind_i.h
index 333ee37..759b020 100644
--- a/include/libunwind_i.h
+++ b/include/libunwind_i.h
@@ -56,6 +56,8 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.  */
 
 #ifdef HAVE_ENDIAN_H
 # include <endian.h>
+#elif defined(HAVE_MACHINE_ENDIAN_H)
+# include <machine/endian.h>
 #else
 # define __LITTLE_ENDIAN	1234
 # define __BIG_ENDIAN		4321
@@ -194,6 +196,10 @@ do {						\
 
 #define SOS_MEMORY_SIZE 16384	/* see src/mi/mempool.c */
 
+#ifndef MAP_ANONYMOUS
+#define MAP_ANONYMOUS MAP_ANON
+#endif
+
 #define GET_MEMORY(mem, size_in_bytes)				    \
 do {									    \
   /* Hopefully, mmap() goes straight through to a system call stub...  */   \
diff --git a/include/remote.h b/include/remote.h
index 9fb90c3..c81f21a 100644
--- a/include/remote.h
+++ b/include/remote.h
@@ -1,6 +1,8 @@
 #ifndef REMOTE_H
 #define REMOTE_H
 
+#define WSIZE	(sizeof (unw_word_t))
+
 /* Helper functions for accessing (remote) memory.  These functions
    assume that all addresses are naturally aligned (e.g., 32-bit
    quantity is stored at a 32-bit-aligned address.  */
@@ -45,8 +47,6 @@ fetchw (unw_addr_space_t as, unw_accessors_t *a,
 
 #else /* !UNW_LOCAL_ONLY */
 
-#define WSIZE	(sizeof (unw_word_t))
-
 static inline int
 fetch8 (unw_addr_space_t as, unw_accessors_t *a,
 	unw_word_t *addr, int8_t *valp, void *arg)
diff --git a/src/Makefile.am b/src/Makefile.am
index e6e3b33..20279d4 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -10,21 +10,13 @@ LIBRARIES_cdep			=
 lib_LTLIBRARIES_cdep		=
 lib_LTLIBRARIES_cdep_setjmp	=
 else
-LIBRARIES_cdep			= libunwind-ptrace.a
+LIBRARIES_cdep			= 
 lib_LTLIBRARIES_cdep		= libunwind.la
 lib_LTLIBRARIES_cdep_setjmp	= libunwind-setjmp.la
 endif
 
 ### libunwind-ptrace:
-libunwind_ptrace_a_SOURCES =						  \
-	ptrace/_UPT_elf.c						  \
-	ptrace/_UPT_internal.h						  \
-	ptrace/_UPT_accessors.c ptrace/_UPT_access_fpreg.c		  \
-	ptrace/_UPT_access_mem.c ptrace/_UPT_access_reg.c		  \
-	ptrace/_UPT_create.c ptrace/_UPT_destroy.c			  \
-	ptrace/_UPT_find_proc_info.c ptrace/_UPT_get_dyn_info_list_addr.c \
-	ptrace/_UPT_put_unwind_info.c ptrace/_UPT_get_proc_name.c	  \
-	ptrace/_UPT_reg_offset.c ptrace/_UPT_resume.c
+libunwind_ptrace_a_SOURCES =
 
 ### libunwind-setjmp:
 libunwind_setjmp_la_LDFLAGS		= $(COMMON_SO_LDFLAGS)		     \
@@ -97,6 +89,8 @@ libunwind_la_SOURCES_os_linux = os-linux.h os-linux.c
 
 libunwind_la_SOURCES_os_hpux = os-hpux.c
 
+libunwind_la_SOURCES_os_freebsd = os-freebsd.h os-freebsd.c
+
 dwarf_SOURCES_common =				\
 	dwarf/global.c
 
@@ -351,6 +345,11 @@ if OS_HPUX
  libunwind_la_SOURCES_os_local	= $(libunwind_la_SOURCES_os_hpux_local)
 endif
 
+if OS_FREEBSD
+ libunwind_la_SOURCES_os	= $(libunwind_la_SOURCES_os_freebsd)
+ libunwind_la_SOURCES_os_local	= $(libunwind_la_SOURCES_os_freebsd_local)
+endif
+
 if ARCH_ARM
  lib_LTLIBRARIES_arch = libunwind-arm.la
  libunwind_la_SOURCES = $(libunwind_la_SOURCES_arm)
diff --git a/src/os-freebsd.c b/src/os-freebsd.c
new file mode 100644
index 0000000..7beabfe
--- /dev/null
+++ b/src/os-freebsd.c
@@ -0,0 +1,41 @@
+/* libunwind - a platform-independent unwind library
+   Copyright (C) 2009 Arun Sharma <aruns@google.com>
+
+This file is part of libunwind.
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+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 OR COPYRIGHT HOLDERS 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.  */
+
+#ifndef UNW_REMOTE_ONLY
+
+#include <limits.h>
+#include <stdio.h>
+
+#include "libunwind_i.h"
+#include "os-freebsd.h"
+
+PROTECTED int
+tdep_get_elf_image (struct elf_image *ei, pid_t pid, unw_word_t ip,
+		    unsigned long *segbase, unsigned long *mapoff)
+{
+  /* Not implemented yet */
+  return -1;
+}
+
+#endif /* UNW_REMOTE_ONLY */
diff --git a/src/os-freebsd.h b/src/os-freebsd.h
new file mode 100644
index 0000000..40a556e
--- /dev/null
+++ b/src/os-freebsd.h
@@ -0,0 +1,28 @@
+/* libunwind - a platform-independent unwind library
+   Copyright (C) 2009 Arun Sharma <aruns@google.com>
+
+This file is part of libunwind.
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+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 OR COPYRIGHT HOLDERS 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.  */
+
+#ifndef os_freebsd_h
+#define os_freebsd_h
+
+#endif /* os_freebsd_h */
diff --git a/src/setjmp/siglongjmp.c b/src/setjmp/siglongjmp.c
index 9a091fa..b2195c9 100644
--- a/src/setjmp/siglongjmp.c
+++ b/src/setjmp/siglongjmp.c
@@ -31,6 +31,11 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.  */
 #include "jmpbuf.h"
 #include "setjmp_i.h"
 
+#ifndef _NSIG
+/* FreeBSD defines it differently */
+#define _NSIG _SIG_MAXSIG
+#endif
+
 void
 siglongjmp (sigjmp_buf env, int val)
 {
diff --git a/src/x86_64/Ginit.c b/src/x86_64/Ginit.c
index 031deaa..ae8a411 100644
--- a/src/x86_64/Ginit.c
+++ b/src/x86_64/Ginit.c
@@ -43,6 +43,7 @@ static struct unw_addr_space local_addr_space;
 
 PROTECTED unw_addr_space_t unw_local_addr_space = &local_addr_space;
 
+#ifdef __linux__
 static inline void *
 uc_addr (ucontext_t *uc, int reg)
 {
@@ -73,6 +74,40 @@ uc_addr (ucontext_t *uc, int reg)
     }
   return addr;
 }
+#elif defined(__FreeBSD__)
+static inline void *
+uc_addr (ucontext_t *uc, int reg)
+{
+  void *addr;
+
+  switch (reg)
+    {
+    case UNW_X86_64_R8: addr = &uc->uc_mcontext.mc_r8; break;
+    case UNW_X86_64_R9: addr = &uc->uc_mcontext.mc_r9; break;
+    case UNW_X86_64_R10: addr = &uc->uc_mcontext.mc_r10; break;
+    case UNW_X86_64_R11: addr = &uc->uc_mcontext.mc_r11; break;
+    case UNW_X86_64_R12: addr = &uc->uc_mcontext.mc_r12; break;
+    case UNW_X86_64_R13: addr = &uc->uc_mcontext.mc_r13; break;
+    case UNW_X86_64_R14: addr = &uc->uc_mcontext.mc_r14; break;
+    case UNW_X86_64_R15: addr = &uc->uc_mcontext.mc_r15; break;
+    case UNW_X86_64_RDI: addr = &uc->uc_mcontext.mc_rdi; break;
+    case UNW_X86_64_RSI: addr = &uc->uc_mcontext.mc_rsi; break;
+    case UNW_X86_64_RBP: addr = &uc->uc_mcontext.mc_rbp; break;
+    case UNW_X86_64_RBX: addr = &uc->uc_mcontext.mc_rbx; break;
+    case UNW_X86_64_RDX: addr = &uc->uc_mcontext.mc_rdx; break;
+    case UNW_X86_64_RAX: addr = &uc->uc_mcontext.mc_rax; break;
+    case UNW_X86_64_RCX: addr = &uc->uc_mcontext.mc_rcx; break;
+    case UNW_X86_64_RSP: addr = &uc->uc_mcontext.mc_rsp; break;
+    case UNW_X86_64_RIP: addr = &uc->uc_mcontext.mc_rip; break;
+
+    default:
+      addr = NULL;
+    }
+  return addr;
+}
+#else
+#error "Unknown OS. Don't know how to decode mcontext"
+#endif
 
 # ifdef UNW_LOCAL_ONLY
 
diff --git a/src/x86_64/Gresume.c b/src/x86_64/Gresume.c
index 0a73441..37677f3 100644
--- a/src/x86_64/Gresume.c
+++ b/src/x86_64/Gresume.c
@@ -35,13 +35,19 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.  */
 
 /* sigreturn() is a no-op on x86_64 glibc.  */
 
+#ifdef __linux__
+#define SYS_SIGRETURN SYS_rt_sigreturn
+#elif defined(__FreeBSD__)
+#define SYS_SIGRETURN SYS_sigreturn
+#endif
+
 static NORETURN inline long
 my_rt_sigreturn (void *new_sp)
 {
   __asm__ __volatile__ ("mov %0, %%rsp;"
 			"mov %1, %%rax;"
 			"syscall"
-			:: "r"(new_sp), "i"(SYS_rt_sigreturn)
+			:: "r"(new_sp), "i"(SYS_SIGRETURN)
 			: "memory");
   abort ();
 }
diff --git a/tests/Makefile.am b/tests/Makefile.am
index f43dc60..30e2b89 100644
--- a/tests/Makefile.am
+++ b/tests/Makefile.am
@@ -100,6 +100,5 @@ Ltest_concurrent_LDADD = $(LIBUNWIND) -lpthread
 Gtest_concurrent_LDADD = $(LIBUNWIND) -lpthread
 test_async_sig_LDADD = $(LIBUNWIND) -lpthread
 
-LDADD += -ldl
 Ltest_nomalloc_SOURCES = Ltest-nomalloc.c
 
diff --git a/tests/mapper.c b/tests/mapper.c
index 1006a8c..423c048 100644
--- a/tests/mapper.c
+++ b/tests/mapper.c
@@ -36,6 +36,10 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.  */
 
 #include <sys/mman.h>
 
+#ifndef MAP_ANONYMOUS
+#define MAP_ANONYMOUS MAP_ANON
+#endif
+
 int
 main (int argc, char **argv)
 {
