Code Monkey home page Code Monkey logo

dmalloc's People

Contributors

aitap avatar ffontaine avatar j256 avatar v-tyrtov avatar xiaoxiang781216 avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

dmalloc's Issues

dmalloc output "not freed: '0x7f2e20d36808|s1' (1182 bytes) from 'unknown'" when using 'printf' and 'fgetc'

Hi,

We have been using dmalloc as part of our tools set to verify that our core libraries are free of memory leaks. However, recently we have discovered that using printf or fgetc would cause dmalloc to throw the following warnings in dmalloc.log.

not freed: '0x7f2e20d36808|s1' (1182 bytes) from 'unknown'

To demonstrate the issue, below is a very simple program that we have used to reproduce the errors:

#include <stdio.h>
#include <stdlib.h>
#include "dmalloc.h"

void main() {
        dmalloc_debug_setup("log-stats,log-non-free,check-fence,log=dmalloc.log");
        printf("Hello World\n");
        fgetc(stdin);
}

Compile the program with:

gcc test.c -ldmalloc -g -o test

Run and I get the following results:

1630587465: 2: Dmalloc version '5.5.2' from 'http://dmalloc.com/'
1630587465: 2: flags = 0x403, logfile 'dmalloc.log'
1630587465: 2: interval = 0, addr = 0, seen # = 0, limit = 0
1630587465: 2: threads enabled, lock-on = 0, lock-init = 2
1630587465: 2: starting time = 1630587464
1630587465: 2: process pid = 2079
1630587465: 2: Dumping Chunk Statistics:
1630587465: 2: basic-block 4096 bytes, alignment 8 bytes
1630587465: 2: heap address range: 0x7f343a6e0000 to 0x7f343a712000, 204800 bytes
1630587465: 2:     user blocks: 4 blocks, 8192 bytes (33%)
1630587465: 2:    admin blocks: 2 blocks, 8192 bytes (33%)
1630587465: 2:    total blocks: 6 blocks, 24576 bytes
1630587465: 2: heap checked 0
1630587465: 2: alloc calls: malloc 2, calloc 0, realloc 0, free 0
1630587465: 2: alloc calls: recalloc 0, memalign 0, posix_memalign 0, valloc 0
1630587465: 2: alloc calls: new 0, delete 0
1630587465: 2:   current memory in use: 8192 bytes (2 pnts)
1630587465: 2:  total memory allocated: 8192 bytes (2 pnts)
1630587465: 2:  max in use at one time: 8192 bytes (2 pnts)
1630587465: 2: max alloced with 1 call: 4096 bytes
1630587465: 2: max unused memory space: 8192 bytes (50%)
1630587465: 2: top 10 allocations:
1630587465: 2:  total-size  count in-use-size  count  source
1630587465: 2:           0      0           0      0  Total of 0
1630587465: 2: Dumping Not-Freed Pointers Changed Since Start:
1630587465: 2:  not freed: '0x7f343a6f0008|s1' (4096 bytes) from 'unknown'
1630587465: 2:  not freed: '0x7f343a710008|s1' (4096 bytes) from 'unknown'
1630587465: 2:  total-size  count  source
1630587465: 2:           0      0  Total of 0
1630587465: 2: ending time = 1630587465, elapsed since start = 0:00:01

Remove the fgetc I got only one warning with memory not being freed.

1630587578: 1: Dumping Not-Freed Pointers Changed Since Start:
1630587578: 1:  not freed: '0x7f939f4e0008|s1' (4096 bytes) from 'unknown'
1630587578: 1:  total-size  count  source
1630587578: 1:           0      0  Total of 0

Remove the printf then I got:

1630587655: 0: Dumping Not-Freed Pointers Changed Since Start:
1630587655: 0:  memory table is empty
1630587655: 0: ending time = 1630587655, elapsed since start = 0:00:00

The gcc version being used here is 9.3.0 and the dmalloc is 5.5.2 which comes with most latest Linux distros when install using their package manager.

NOTE

  1. This is also observed when compiled with g++.
  2. Some people have pointed out that the library 5.5.2 is quite old. I have build the latest version 5.6.5 and test with gcc 11.2.0 and the problem still persists.
1630589888: 2: Dmalloc version '5.6.5' from 'http://dmalloc.com/'
1630589888: 2: flags = 0x403, logfile 'dmalloc.log'
1630589888: 2: interval = 0, addr = 0x0, seen # = 0, limit = 0
1630589888: 2: starting time = 1630589886
1630589888: 2: process pid = 11185
1630589888: 2: Dumping Chunk Statistics:
1630589888: 2: basic-block 4096 bytes, alignment 8 bytes
1630589888: 2: heap address range: 0x7ff82bd98000 to 0x7ff82bd9b000, 12288 bytes
1630589888: 2:     user blocks: 1 blocks, 2048 bytes (16%)
1630589888: 2:    admin blocks: 2 blocks, 8192 bytes (67%)
1630589888: 2:    total blocks: 3 blocks, 12288 bytes
1630589888: 2: heap checked 0
1630589888: 2: alloc calls: malloc 2, calloc 0, realloc 0, free 0
1630589888: 2: alloc calls: recalloc 0, memalign 0, valloc 0
1630589888: 2: alloc calls: new 0, delete 0
1630589888: 2:   current memory in use: 2048 bytes (2 pnts)
1630589888: 2:  total memory allocated: 2048 bytes (2 pnts)
1630589888: 2:  max in use at one time: 2048 bytes (2 pnts)
1630589888: 2: max alloced with 1 call: 1024 bytes
1630589888: 2: max unused memory space: 2048 bytes (50%)
1630589888: 2: top 10 allocations:
1630589888: 2:  total-size  count in-use-size  count  source
1630589888: 2:           0      0           0      0  Total of 0
1630589888: 2: Dumping Not-Freed Pointers Changed Since Start:
1630589888: 2:  not freed: '0x7ff82bd9a008|s1' (1024 bytes) from 'unknown'
1630589888: 2:  not freed: '0x7ff82bd9a808|s1' (1024 bytes) from 'unknown'
1630589888: 2:  total-size  count  source
1630589888: 2:           0      0  Total of 0
1630589888: 2: ending time = 1630589888, elapsed since start = 0:00:02

stack overflow in dmalloc_die

Greetings,

I would like to ask if the issue drok/ovpn#7 is known. It appears that when free(pnt=0x0) is called, dmalloc gets into an infinite recursive loop that eventually overflows the process stack.

I have absolutely no experience with dmalloc, so it's possible the error is in my usage; if so, I would appreciate any feedback.

Docs missing from 5.6.0?

Hi, I maintain this package for Mageia and seem to be having problems finding the docs. Am I missing something or is the tarball missing something?

Feature request: native Windows support

I have a Windows-only project that dmalloc could really help with. Currently, it seems that the only way to use dmalloc on Windows is to build it with Cygwin, since the only virtual memory APIs that dmalloc currently speaks are sbrk and mmap, and Windows has neither.

If you are interested in this, I could prepare a pull request modifying heap.c to use VirtualAlloc / VirtualFree in addition to mmap / munmap, bringing me closer to my goal of cross-compiling dmalloc for Windows using something like ./configure --build=i686-linux-gnu --host=i686-w64-mingw32. While lack of mmap could be worked around using INTERNAL_MEMORY_SPACE, it's not a good solution.

cannot install dmalloc

i cannot find the test result file: logfile.

my compile cmd is:
gcc -DDMALLOC -DDMALLOC_FUNC_CHECK -ldmalloc -I/usr/local/include/libbson-1.0 -I/usr/local/include/libmongoc-1.0 -lmongoc-1.0 -lbson-1.0 test.c

can you help me?

thank you!

installdocs issues

make installdocs returns:

make[2]: don't know how to make ./dmalloc.info. Stop

I think the issue is that there's a rule in Makefile.in for dmalloc.info via INFOFILE but not one for ./dmalloc.info.

In Makefile.in:

-installdocs : $(srcdir)/$(HTMLFILE) $(srcdir)/$(INFOFILE)
+installdocs : $(srcdir)/$(HTMLFILE) $(INFOFILE)

 $(INFOFILE) : $(srcdir)/dmalloc.texi
 	rm -f $@ [email protected]
-	makeinfo -o [email protected] --fill-column=100 --no-split $<
+	makeinfo -o [email protected] --fill-column=100 --no-split $(srcdir)/dmalloc.texi

fixes it for me.

BTW, DOCFILES specifies non-existent documentation files, and is only used in an echo statement.

Installing fails with 'multiple definition' during shared library building

As a first time user of dmalloc 5.5.2, I encountered the following "multiple definition" error while building the shared library target "installsl":

bc6:radu [Linux] /tmp/dmalloc
$ ./configure --prefix=/tmp/dmalloc-root/usr
[... success ...]
$ make install installsl
rm -f dmalloc.h dmalloc.h.t
cat ./dmalloc.h.1 dmalloc.h.2 ./dmalloc.h.3 > dmalloc.h.t
mv dmalloc.h.t dmalloc.h
./mkinstalldirs /tmp/dmalloc-root/usr/include
/usr/bin/install -c -m 644 dmalloc.h /tmp/dmalloc-root/usr/include
rm -f arg_check.o
gcc -g -O2  -DHAVE_STDARG_H=1 -DHAVE_STDLIB_H=1 -DHAVE_STRING_H=1 -DHAVE_UNISTD_H=1 -DHAVE_SYS_MMAN_H=1 -DHAVE_SYS_TYPES_H=1 -DHAVE_W32API_WINBASE_H=0 -DHAVE_W32API_WINDEF_H=0 -DHAVE_SYS_CYGWIN_H=0 -DHAVE_SIGNAL_H=1  -I. -I.  -c arg_check.c -o ./arg_check.o
rm -f compat.o
gcc -g -O2  -DHAVE_STDARG_H=1 -DHAVE_STDLIB_H=1 -DHAVE_STRING_H=1 -DHAVE_UNISTD_H=1 -DHAVE_SYS_MMAN_H=1 -DHAVE_SYS_TYPES_H=1 -DHAVE_W32API_WINBASE_H=0 -DHAVE_W32API_WINDEF_H=0 -DHAVE_SYS_CYGWIN_H=0 -DHAVE_SIGNAL_H=1  -I. -I.  -c compat.c -o ./compat.o
rm -f dmalloc_rand.o
gcc -g -O2  -DHAVE_STDARG_H=1 -DHAVE_STDLIB_H=1 -DHAVE_STRING_H=1 -DHAVE_UNISTD_H=1 -DHAVE_SYS_MMAN_H=1 -DHAVE_SYS_TYPES_H=1 -DHAVE_W32API_WINBASE_H=0 -DHAVE_W32API_WINDEF_H=0 -DHAVE_SYS_CYGWIN_H=0 -DHAVE_SIGNAL_H=1  -I. -I.  -c dmalloc_rand.c -o ./dmalloc_rand.o
rm -f dmalloc_tab.o
gcc -g -O2  -DHAVE_STDARG_H=1 -DHAVE_STDLIB_H=1 -DHAVE_STRING_H=1 -DHAVE_UNISTD_H=1 -DHAVE_SYS_MMAN_H=1 -DHAVE_SYS_TYPES_H=1 -DHAVE_W32API_WINBASE_H=0 -DHAVE_W32API_WINDEF_H=0 -DHAVE_SYS_CYGWIN_H=0 -DHAVE_SIGNAL_H=1  -I. -I.  -c dmalloc_tab.c -o ./dmalloc_tab.o
rm -f env.o
gcc -g -O2  -DHAVE_STDARG_H=1 -DHAVE_STDLIB_H=1 -DHAVE_STRING_H=1 -DHAVE_UNISTD_H=1 -DHAVE_SYS_MMAN_H=1 -DHAVE_SYS_TYPES_H=1 -DHAVE_W32API_WINBASE_H=0 -DHAVE_W32API_WINDEF_H=0 -DHAVE_SYS_CYGWIN_H=0 -DHAVE_SIGNAL_H=1  -I. -I.  -c env.c -o ./env.o
rm -f heap.o
gcc -g -O2  -DHAVE_STDARG_H=1 -DHAVE_STDLIB_H=1 -DHAVE_STRING_H=1 -DHAVE_UNISTD_H=1 -DHAVE_SYS_MMAN_H=1 -DHAVE_SYS_TYPES_H=1 -DHAVE_W32API_WINBASE_H=0 -DHAVE_W32API_WINDEF_H=0 -DHAVE_SYS_CYGWIN_H=0 -DHAVE_SIGNAL_H=1  -I. -I.  -c heap.c -o ./heap.o
rm -f chunk.o
gcc -g -O2  -DHAVE_STDARG_H=1 -DHAVE_STDLIB_H=1 -DHAVE_STRING_H=1 -DHAVE_UNISTD_H=1 -DHAVE_SYS_MMAN_H=1 -DHAVE_SYS_TYPES_H=1 -DHAVE_W32API_WINBASE_H=0 -DHAVE_W32API_WINDEF_H=0 -DHAVE_SYS_CYGWIN_H=0 -DHAVE_SIGNAL_H=1  -I. -I.  -c chunk.c -o ./chunk.o
rm -f error.o
gcc -g -O2  -DHAVE_STDARG_H=1 -DHAVE_STDLIB_H=1 -DHAVE_STRING_H=1 -DHAVE_UNISTD_H=1 -DHAVE_SYS_MMAN_H=1 -DHAVE_SYS_TYPES_H=1 -DHAVE_W32API_WINBASE_H=0 -DHAVE_W32API_WINDEF_H=0 -DHAVE_SYS_CYGWIN_H=0 -DHAVE_SIGNAL_H=1  -I. -I.  -c error.c -o ./error.o
rm -f malloc.o
gcc -g -O2  -DHAVE_STDARG_H=1 -DHAVE_STDLIB_H=1 -DHAVE_STRING_H=1 -DHAVE_UNISTD_H=1 -DHAVE_SYS_MMAN_H=1 -DHAVE_SYS_TYPES_H=1 -DHAVE_W32API_WINBASE_H=0 -DHAVE_W32API_WINDEF_H=0 -DHAVE_SYS_CYGWIN_H=0 -DHAVE_SIGNAL_H=1  -I. -I.  -c malloc.c -o ./malloc.o
ar cr libdmalloc.a arg_check.o compat.o dmalloc_rand.o dmalloc_tab.o env.o heap.o chunk.o error.o malloc.o
ranlib libdmalloc.a
./mkinstalldirs /tmp/dmalloc-root/usr/lib
/usr/bin/install -c libdmalloc.a /tmp/dmalloc-root/usr/lib
ranlib /tmp/dmalloc-root/usr/lib/libdmalloc.a
Enter 'make installsl' to install libdmalloc.so in /tmp/dmalloc-root/usr/lib
Enter 'make installcxx' to install the C++ library
Enter 'make installth' to install thread library
rm -f dmalloc.o
gcc -g -O2  -DHAVE_STDARG_H=1 -DHAVE_STDLIB_H=1 -DHAVE_STRING_H=1 -DHAVE_UNISTD_H=1 -DHAVE_SYS_MMAN_H=1 -DHAVE_SYS_TYPES_H=1 -DHAVE_W32API_WINBASE_H=0 -DHAVE_W32API_WINDEF_H=0 -DHAVE_SYS_CYGWIN_H=0 -DHAVE_SIGNAL_H=1  -I. -I.  -c dmalloc.c -o ./dmalloc.o
rm -f dmalloc_argv.o
gcc -g -O2  -DHAVE_STDARG_H=1 -DHAVE_STDLIB_H=1 -DHAVE_STRING_H=1 -DHAVE_UNISTD_H=1 -DHAVE_SYS_MMAN_H=1 -DHAVE_SYS_TYPES_H=1 -DHAVE_W32API_WINBASE_H=0 -DHAVE_W32API_WINDEF_H=0 -DHAVE_SYS_CYGWIN_H=0 -DHAVE_SIGNAL_H=1  -I. -I.  -c dmalloc_argv.c -o ./dmalloc_argv.o
rm -f dmalloc
gcc  -o aout dmalloc.o dmalloc_argv.o compat.o env.o \
                -L.
mv aout dmalloc
./mkinstalldirs /tmp/dmalloc-root/usr/bin
/usr/bin/install -c dmalloc /tmp/dmalloc-root/usr/bin
Enter 'make installdocs' to install dmalloc.html dmalloc.texi dmalloc.pdf in /tmp/dmalloc-root/usr/share/doc/dmalloc
rm -f libdmalloc.so libdmalloc.so.t
ld -shared --whole-archive -soname libdmalloc.so -o libdmalloc.so.t libdmalloc.a arg_check.o compat.o dmalloc_rand.o dmalloc_tab.o env.o heap.o
arg_check.o: In function `_dmalloc_strlen':
/tmp/dmalloc/arg_check.c:446: multiple definition of `_dmalloc_strlen'
libdmalloc.a(arg_check.o):/tmp/dmalloc/arg_check.c:446: first defined here
arg_check.o: In function `_dmalloc_strtok':
/tmp/dmalloc/arg_check.c:669: multiple definition of `_dmalloc_strtok'
libdmalloc.a(arg_check.o):/tmp/dmalloc/arg_check.c:669: first defined here
arg_check.o: In function `_dmalloc_strstr':
/tmp/dmalloc/arg_check.c:650: multiple definition of `_dmalloc_strstr'
libdmalloc.a(arg_check.o):/tmp/dmalloc/arg_check.c:650: first defined here

To get around it, I had to make this change to Makefile.in, which allowed the installation:

diff --git a/Makefile.in b/Makefile.in
index f49c6f9..a60f139 100644
--- a/Makefile.in
+++ b/Makefile.in
@@ -302,7 +302,7 @@ shlib : $(BUILD_SL)
 # via: http://256.com/gray/email.html
 $(LIB_SL) : $(LIBRARY)
        rm -f $@ [email protected]
-       @shlinkargs@ $(LIBRARY) $(OBJS) $(NORMAL_OBJS)
+       @shlinkargs@ $(LIBRARY)
        mv [email protected] $@

 $(LIBRARY) : $(OBJS) $(NORMAL_OBJS)
@@ -315,7 +315,7 @@ $(LIB_TH) : $(OBJS) $(THREAD_OBJS)

 $(LIB_TH_SL) : $(LIB_TH)
        rm -f $@ [email protected]
-       @shlinkargs@ $(LIB_TH) $(OBJS) $(THREAD_OBJS)
+       @shlinkargs@ $(LIB_TH)
        mv [email protected] $@

 $(LIB_CXX) : $(OBJS) $(NORMAL_OBJS) $(CXX_OBJS)

This may be related to #4 as the unit test that triggers that issue is linked against the shared library built with the patch above.

Mulitple discontinuous memory region support

In the embeded system without MMU, it's very common that many memory regions exist, so It's will be very useful if dmalloc can support it. Actually, we have sucessfully ported dmalloc to a popular RTOS(https://github.com/apache/incubator-nuttx) which has a clean multiple heap interface(https://github.com/apache/incubator-nuttx/blob/master/include/nuttx/mm/mm.h):

void mm_initialize(FAR struct mm_heap_s *heap, FAR void *heap_start,
                   size_t heap_size);
void mm_addregion(FAR struct mm_heap_s *heap, FAR void *heapstart,
                  size_t heapsize);
FAR void *mm_malloc(FAR struct mm_heap_s *heap, size_t size);
void mm_free(FAR struct mm_heap_s *heap, FAR void *mem);
FAR void *mm_realloc(FAR struct mm_heap_s *heap, FAR void *oldmem,
                     size_t size);
FAR void *mm_calloc(FAR struct mm_heap_s *heap, size_t n, size_t elem_size);
FAR void *mm_zalloc(FAR struct mm_heap_s *heap, size_t size);
FAR void *mm_memalign(FAR struct mm_heap_s *heap, size_t alignment,
                      size_t size);
bool mm_heapmember(FAR struct mm_heap_s *heap, FAR void *mem);
FAR void *mm_brkaddr(FAR struct mm_heap_s *heap, int region);
FAR void *mm_sbrk(FAR struct mm_heap_s *heap, intptr_t incr,
                  uintptr_t maxbreak);
void mm_extend(FAR struct mm_heap_s *heap, FAR void *mem, size_t size,
               int region);
int mm_mallinfo(FAR struct mm_heap_s *heap, FAR struct mallinfo *info);

The idea is that:

  1. Move heap related global variables into one struct(e.g. dlmalloc_heap)
  2. Add a new set of API accept dlmalloc_heap as argument, e.g.:
extern
DMALLOC_PNT	dmalloc_heap_malloc(dlmalloc_heap *heap, const char *file, const int line, 
			       const DMALLOC_SIZE size, const int func_id,
			       const DMALLOC_SIZE alignment,
			       const int xalloc_b);
  1. Define a global default heap and implement dmalloc_malloc like this:
static dlmalloc_heap heap:

DMALLOC_PNT	dmalloc_malloc(const char *file, const int line,
			       const DMALLOC_SIZE size, const int func_id,
			       const DMALLOC_SIZE alignment,
			       const int xalloc_b)
{
	return dmalloc_heap_malloc(&heap, file, line, size, func_id, alignment, xalloc_b);
}

With this change install, it will be easy to replace dlmalloc in the embeded environment.

loc_snprintf implementation uses va_args innappropriately

Copied from #23 . Thanks much to @aitap

Functions in append.c pass va_lists to other functions, expecting state modifications done by va_arg() in the callee to persist in the caller. Apparently this is not the case for mingw (where va_list could be just a char *), so loc_snprintf(setup, sizeof(setup), "debug=%#x,start=%s:%d", 0x400, loc_file, loc_line); crashes while trying to dereference 0x400 instead of loc_file.

installdocs seems broken

In the dmalloc-5.6.0 release, the installdocs target looks as follows:

installdocs : $(srcdir)/docs/$(HTMLFILE) $(srcdir)/docs/$(TEXIFILE)
$(srcdir)/docs/$(PDFFILE)
$(srcdir)/mkinstalldirs $(docdir)
$(INSTALL_DATA) $(srcdir)/docs/$(HTMLFILE) $(docdir)
$(INSTALL_DATA) $(srcdir)/docs/$(TEXIFILE) $(docdir)
$(INSTALL_DATA) $(srcdir)/docs/$(PDFFILE) $(docdir)

the docs directory doesn't exist in the release tar. the html and texi file are in $(srcdir), though the pdf file is not.

Not building on ubuntu 16.04

gcc --version
gcc (Ubuntu 8.1.0-5ubuntu1~16.04) 8.1.0

make
rm -f arg_check.o
gcc -g -O2 -DHAVE_STDARG_H=1 -DHAVE_STDLIB_H=1 -DHAVE_STRING_H=1 -DHAVE_UNISTD_H=1 -DHAVE_SYS_MMAN_H=1 -DHAVE_SYS_TYPES_H=1 -DHAVE_W32API_WINBASE_H=0 -DHAVE_W32API_WINDEF_H=0 -DHAVE_SYS_CYGWIN_H=0 -DHAVE_SIGNAL_H=1 -I. -I. -c arg_check.c -o ./arg_check.o
In file included from /usr/include/string.h:630,
from arg_check.c:31:
dmalloc.h:482:7: error: expected identifier or ‘(’ before ‘extension
char *strndup(const char *string, const DMALLOC_SIZE len);
^~~~~~~
Makefile:407: recipe for target 'arg_check.o' failed
make: *** [arg_check.o] Error 1

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.