#1 Step: install valgrind
[cx@blog]$ apt-get install valgrind
#2 Step: create a C program (leak.c)
--------------------------------------------------------------------------------------------
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main() {
char *str;
/* memory allocation */
str = (char *)malloc(10);
if (str == NULL) {
exit(EXIT_FAILURE);
}
strcpy(str, "kondukto");
printf("String: %s, Address = %u\n", str, str);
/* free resource */
free(str);
return 0;
}
--------------------------------------------------------------------------------------------
#3 Step: Compile the C program and run
[cx@blog]$ gcc leak.c -o leak
[cx@blog]$ ./leak
String: kondukto, Address = 2087920224
#4 Step: Run valgrind and check the memory
[cx@blog]$ valgrind --leak-check=full -v ./leak
*snip*
==24737== HEAP SUMMARY:
==24737== in use at exit: 0 bytes in 0 blocks
==24737== total heap usage: 2 allocs, 2 frees, 1,034 bytes allocated
==24737==
==24737== All heap blocks were freed -- no leaks are possible
*snip*
#4 Step: Run valgrind and check the memory
[cx@blog]$ valgrind --leak-check=full -v ./leak
*snip*
==24737== HEAP SUMMARY:
==24737== in use at exit: 0 bytes in 0 blocks
==24737== total heap usage: 2 allocs, 2 frees, 1,034 bytes allocated
==24737==
==24737== All heap blocks were freed -- no leaks are possible
*snip*
#5 Step: Comment out “free(str)”;
---------------------------------------------------------------------------
/* free resource */
//free(str);
---------------------------------------------------------------------------
#6 Step: Compile the C program
[cx@blog]$ gcc leak.c -o leak
#7 Step: Run valgrind and check the memory
[cx@blog]$ valgrind --leak-check=full -v ./leak
*snip*
==24814== HEAP SUMMARY:
==24814== in use at exit: 10 bytes in 1 blocks
==24814== total heap usage: 2 allocs, 1 frees, 1,034 bytes allocated
==24737==
==24814== 10 bytes in 1 blocks are definitely lost in loss record 1 of 1
==24814== at 0x483777F: malloc (vg_replace_malloc.c:299)
==24814== by 0x10906D: main (in /tmp/blog/leak)
==24814==
==24814== LEAK SUMMARY:
==24814== definitely lost: 10 bytes in 1 blocks
==24814== indirectly lost: 0 bytes in 0 blocks
==24814== possibly lost: 0 bytes in 0 blocks
==24814== still reachable: 0 bytes in 0 blocks
==24814== suppressed: 0 bytes in 0 blocks
==24814==
==24814== For counts of detected and suppressed errors, rerun with: -v
==24814== ERROR SUMMARY: 1 errors from 1 contexts (suppressed: 0 from 0)
*snip*
#1 Step: Write a GO program (gctest.go)
-----------------------------------------------------------------
package main
import (
"fmt"
"time"
)
func login(passwd string) bool {
time.Sleep(500 * time.Millisecond)
if len(passwd) > 0 {
return true
}
return false
}
func main() {
for i := 0; i < 5; i++ {
go func() {
user := fmt.Sprintf("user-%d-password", i)
if login(user) {
fmt.Println("success")
}
}()
time.Sleep(time.Second)
}
}
-----------------------------------------------------------------
#2 Step: Build it
[cx@cxpc blog]$ go build gctest.go
#3 Step Create a dump.sh file:
To dump the memory we will use a simple bash script which reads memory regions from
/proc/<pid>/maps and will use gdb to dump the content.
#4 Step Run go code and dump the memory:
[cx@blog]$ ./gctest # in one terminal
[cx@blog]$ sudo ./dump.sh `ps ax|grep gctest|awk '{print $1;exit}'` # other term
#5 Step investigate memory:
[cx@blog]$ grep "password*" *.dump
Binary file 8864-c41fff8000-c420100000.dump matches
[cx@blog]$ hexdump -C 8864-c41fff8000-c420100000.dump |grep -A5 password
*
000ae000 75 73 65 72 2d 31 73 0a 01 00 00 00 00 00 00 00 |user-1s.........|
000ae010 75 73 65 72 2d 33 2d 70 61 73 73 77 6f 72 64 00 |user-3-password.|
000ae020 75 73 65 72 2d 31 2d 70 61 73 73 77 6f 72 64 00 |user-1-password.|
000ae030 03 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 |................|
000ae040 75 73 65 72 2d 33 2d 70 61 73 73 77 6f 72 64 00 |user-3-password.|
000ae050 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 |................|
*