Repository: Konstantin8105/c4go
Pull request #358 (2019-03-25 12:16:22)

unification pointer arithmetic approach

codecov[bot]: # [Codecov](https://codecov.io/gh/Konstantin8105/c4go/pull/358?src=pr&el=h1) Report
> Merging [#358](https://codecov.io/gh/Konstantin8105/c4go/pull/358?src=pr&el=desc) into [master](https://codecov.io/gh/Konstantin8105/c4go/commit/52d5c5f4bccd7eea5db7248609c81155d8d2d38a?src=pr&el=desc) will **decrease** coverage by `0.44%`.
> The diff coverage is `77.44%`.

[![Impacted file tree graph](https://codecov.io/gh/Konstantin8105/c4go/pull/358/graphs/tree.svg?width=650&token=esH2rHXlZ2&height=150&src=pr)](https://codecov.io/gh/Konstantin8105/c4go/pull/358?src=pr&el=tree)

```diff
@@            Coverage Diff             @@
##           master     #358      +/-   ##
==========================================
- Coverage    86.3%   85.85%   -0.45%     
==========================================
  Files         186      186              
  Lines       10730    10912     +182     
==========================================
+ Hits         9260     9368     +108     
- Misses       1051     1101      +50     
- Partials      419      443      +24
```


| [Impacted Files](https://codecov.io/gh/Konstantin8105/c4go/pull/358?src=pr&el=tree) | Coverage Δ | |
|---|---|---|
| [util/goast.go](https://codecov.io/gh/Konstantin8105/c4go/pull/358/diff?src=pr&el=tree#diff-dXRpbC9nb2FzdC5nbw==) | `86.93% <0%> (-3.47%)` | :arrow_down: |
| [transpiler/variables.go](https://codecov.io/gh/Konstantin8105/c4go/pull/358/diff?src=pr&el=tree#diff-dHJhbnNwaWxlci92YXJpYWJsZXMuZ28=) | `84.9% <100%> (+0.69%)` | :arrow_up: |
| [noarch/string.go](https://codecov.io/gh/Konstantin8105/c4go/pull/358/diff?src=pr&el=tree#diff-bm9hcmNoL3N0cmluZy5nbw==) | `86.13% <100%> (+0.57%)` | :arrow_up: |
| [transpiler/unary.go](https://codecov.io/gh/Konstantin8105/c4go/pull/358/diff?src=pr&el=tree#diff-dHJhbnNwaWxlci91bmFyeS5nbw==) | `74.59% <100%> (ø)` | :arrow_up: |
| [transpiler/operators.go](https://codecov.io/gh/Konstantin8105/c4go/pull/358/diff?src=pr&el=tree#diff-dHJhbnNwaWxlci9vcGVyYXRvcnMuZ28=) | `80.8% <100%> (+0.65%)` | :arrow_up: |
| [transpiler/call.go](https://codecov.io/gh/Konstantin8105/c4go/pull/358/diff?src=pr&el=tree#diff-dHJhbnNwaWxlci9jYWxsLmdv) | `79.89% <100%> (+0.1%)` | :arrow_up: |
| [transpiler/binary.go](https://codecov.io/gh/Konstantin8105/c4go/pull/358/diff?src=pr&el=tree#diff-dHJhbnNwaWxlci9iaW5hcnkuZ28=) | `71.98% <58.33%> (-3.55%)` | :arrow_down: |
| [transpiler/cast.go](https://codecov.io/gh/Konstantin8105/c4go/pull/358/diff?src=pr&el=tree#diff-dHJhbnNwaWxlci9jYXN0Lmdv) | `76.33% <75%> (-0.54%)` | :arrow_down: |
| [transpiler/value\_to\_pointer.go](https://codecov.io/gh/Konstantin8105/c4go/pull/358/diff?src=pr&el=tree#diff-dHJhbnNwaWxlci92YWx1ZV90b19wb2ludGVyLmdv) | `83.2% <79.86%> (-11.06%)` | :arrow_down: |
| [transpiler/functions.go](https://codecov.io/gh/Konstantin8105/c4go/pull/358/diff?src=pr&el=tree#diff-dHJhbnNwaWxlci9mdW5jdGlvbnMuZ28=) | `84.47% <0%> (-4.57%)` | :arrow_down: |
| ... and [4 more](https://codecov.io/gh/Konstantin8105/c4go/pull/358/diff?src=pr&el=tree-more) | |

------

[Continue to review full report at Codecov](https://codecov.io/gh/Konstantin8105/c4go/pull/358?src=pr&el=continue).
> **Legend** - [Click here to learn more](https://docs.codecov.io/docs/codecov-delta)
> `Δ = absolute <relative> (impact)`, `ø = not affected`, `? = missing data`
> Powered by [Codecov](https://codecov.io/gh/Konstantin8105/c4go/pull/358?src=pr&el=footer). Last update [52d5c5f...c617864](https://codecov.io/gh/Konstantin8105/c4go/pull/358?src=pr&el=lastupdated). Read the [comment docs](https://docs.codecov.io/docs/pull-request-comments).


Patch:
diff --git a/main.go b/main.go
index 172d6e0..cba528a 100644
--- a/main.go
+++ b/main.go
@@ -216,7 +216,7 @@ var goKeywords = [...]string{
 	"fallthrough", "if", "range", "type", "continue", "for",
 	"import", "return", "var", "init",
 	// "struct",
-	// "_",
+	"_",
 	// "const",
 	// go packages
 	"fmt", "os", "math", "testing", "unsafe", "ioutil",
@@ -230,6 +230,11 @@ var goKeywords = [...]string{
 	"uint", "uintptr",
 	"float32", "float64",
 	"complex64", "complex128",
+	// built-in
+	"len", "append", "cap", "delete", "copy", // "close",
+	"make", "new", "panic", "recover", "real", "complex",
+	"imag", "print", "println", "error", "Type", "Type1",
+	"IntegerType", "FloatType", "ComplexType",
 }
 var letters string = "_qwertyuiopasdfghjklzxcvbnm1234567890><"
 
diff --git a/noarch/string.go b/noarch/string.go
index b352505..0998d65 100644
--- a/noarch/string.go
+++ b/noarch/string.go
@@ -212,8 +212,14 @@ func Strrchr(source []byte, c32 int32) []byte {
 	return source
 }
 
-func Strdup(s []byte) []byte {
-	return s
+func Strdup(s []byte) (rs []byte) {
+	for i := range s {
+		if s[i] == '\x00' {
+			break
+		}
+		rs = append(rs, s[i])
+	}
+	return
 }
 
 func Strerror(e int32) []byte {
diff --git a/scripts/scripts.txt b/scripts/scripts.txt
index cd826bf..7b706fe 100644
--- a/scripts/scripts.txt
+++ b/scripts/scripts.txt
@@ -1,46 +1,46 @@
 
 Calculate warnings : ./testdata/9wm
-		After transpiling : 5 warnings.
+		After transpiling : 4 warnings.
 		Go build : 12 warnings
-		Unsafe   : 371
+		Unsafe   : 407
 
 Calculate warnings : ./testdata/ed
-		After transpiling : 4 warnings.
+		After transpiling : 3 warnings.
 		Go build : 2 warnings
-		Unsafe   : 156
+		Unsafe   : 169
 
 Calculate warnings in file: ./testdata/neateqn/neateqn.go
 		After transpiling : 0 warnings.
-		Go build : 4 warnings
-		Unsafe   : 15
+		Go build : 0 warnings
+		Unsafe   : 22
 
 Calculate warnings in file: ./testdata/neatmkfn/neatmkfn.go
 		After transpiling : 557 warnings.
 		Go build : 75 warnings
-		Unsafe   : 19
+		Unsafe   : 44
 
 Calculate warnings in file: ./testdata/neatpost/neatpost.go
-		After transpiling : 2 warnings.
-		Go build : 51 warnings
-		Unsafe   : 28
+		After transpiling : 4 warnings.
+		Go build : 46 warnings
+		Unsafe   : 39
 
 Calculate warnings in file: ./testdata/neatrefer/neatrefer.go
 		After transpiling : 2 warnings.
-		Go build : 2 warnings
-		Unsafe   : 12
+		Go build : 0 warnings
+		Unsafe   : 14
 
 Calculate warnings in file: ./testdata/neatroff/neatroff.go
-		After transpiling : 4 warnings.
-		Go build : 48 warnings
-		Unsafe   : 170
+		After transpiling : 9 warnings.
+		Go build : 21 warnings
+		Unsafe   : 201
 
 Calculate warnings in file: ./testdata/neatvi/neatvi.go
-		After transpiling : 31 warnings.
-		Go build : 3 warnings
-		Unsafe   : 79
+		After transpiling : 34 warnings.
+		Go build : 2 warnings
+		Unsafe   : 130
 
 Calculate warnings in file: testdata/vorbis/vorbis.go
 After transpiling : 5 warnings.
-		Go build : 180 warnings
-		Unsafe   : 69
+		Go build : 43 warnings
+		Unsafe   : 203
 
diff --git a/transpiler/binary.go b/transpiler/binary.go
index dbba7f4..48dfca1 100644
--- a/transpiler/binary.go
+++ b/transpiler/binary.go
@@ -299,14 +299,66 @@ func transpileBinaryOperator(n *ast.BinaryOperator, p *program.Program, exprIsSt
 		err = fmt.Errorf("cannot atomic for right part. %v", err)
 		return nil, "unknown53", nil, nil, err
 	}
-	if types.IsPointer(leftType, p) && types.IsPointer(rightType, p) && operator == token.SUB {
-		p.AddImport("unsafe")
-		sizeof, err := types.SizeOf(p, types.GetBaseType(leftType))
-		if err != nil {
-			return nil, "unknown53", nil, nil, err
+
+	if types.IsPointer(leftType, p) && types.IsPointer(rightType, p) {
+		switch operator {
+		case token.SUB: // -
+			p.AddImport("unsafe")
+			var sizeof int
+			sizeof, err = types.SizeOf(p, types.GetBaseType(leftType))
+			if err != nil {
+				return nil, "PointerOperation_unknown01", nil, nil, err
+			}
+			var e goast.Expr
+			var newPost []goast.Stmt
+			e, newPost, err = SubTwoPnts(left, leftType, right, rightType, sizeof)
+			if err != nil {
+				return nil, "PointerOperation_unknown02", nil, nil, err
+			}
+			postStmts = append(postStmts, newPost...)
+
+			expr, err = types.CastExpr(p, e, "long long", n.Type)
+			if err != nil {
+				return nil, "PointerOperation_unknown03", nil, nil, err
+			}
+			eType = n.Type
+			return
+
+		case token.GTR, token.GEQ, // >  >=
+			token.LOR,            // ||
+			token.LAND,           // &&
+			token.LSS, token.LEQ, // <  <=
+			token.EQL, token.NEQ: // == !=
+
+			var sizeof int
+			sizeof, err = types.SizeOf(p, types.GetBaseType(leftType))
+			if err != nil {
+				return nil, "PointerOperation_unknown04", nil, nil, err
+			}
+			var e goast.Expr
+			var newPost []goast.Stmt
+			e, newPost, err = PntCmpPnt(
+				p,
+				left, leftType,
+				right, rightType,
+				sizeof, operator,
+			)
+			if err != nil {
+				return nil, "PointerOperation_unknown05", nil, nil, err
+			}
+			postStmts = append(postStmts, newPost...)
+			expr = e
+			eType = "bool"
+
+			return
+
+		case token.ASSIGN: // =
+			// ignore
+
+		default:
+			err = fmt.Errorf("Not implemented pointer operation: %v", operator)
+			return
 		}
-		left, leftType = util.GetUintptrForSlice(left, sizeof)
-		right, rightType = util.GetUintptrForSlice(right, sizeof)
 	}
 
 	preStmts, postStmts = combinePreAndPostStmts(preStmts, postStmts, newPre, newPost)
@@ -450,52 +502,47 @@ func transpileBinaryOperator(n *ast.BinaryOperator, p *program.Program, exprIsSt
 			// | `-DeclRefExpr 'char *' lvalue Var 0x26ba988 'c' 'char *'
 			// `-ImplicitCastExpr 'char *' <LValueToRValue>
 			//   `-DeclRefExpr 'char *' lvalue Var 0x26ba8a8 'b' 'char *'
-			if types.IsCPointer(leftType, p) || types.IsCArray(leftType, p) {
-				left = util.GetUintptr(left)
-				right = util.GetUintptr(right)
-				p.AddImport("unsafe")
+			if types.IsPointer(leftType, p) || types.IsPointer(rightType, p) {
+				err = fmt.Errorf("need add pointer operator : %s %v %s",
+					leftType, n.Operator, rightType)
+				return
 			}
 		}
 	}
 
 	if operator == token.ASSIGN { // =
-		// Memory allocation is translated into the Go-style.
-		allocSize := getAllocationSizeNode(p, n.Children()[1])
 
-		if allocSize != nil {
-			right, newPre, newPost, err = generateAlloc(p, allocSize, leftType)
-			if err != nil {
-				p.AddMessage(p.GenerateWarningMessage(err, n))
-				return nil, "", nil, nil, err
-			}
+		// BinaryOperator 'double *' '='
+		// |-DeclRefExpr 'double *' lvalue Var 0x2a7fa48 'd' 'double *'
+		// `-ImplicitCastExpr 'double *' <BitCast>
+		//   `-CStyleCastExpr 'char *' <BitCast>
+		//     `-...
+		right, err = types.CastExpr(p, right, rightType, returnType)
+		rightType = returnType
+		if err != nil {
+			return
+		}
 
-			preStmts, postStmts = combinePreAndPostStmts(preStmts, postStmts, newPre, newPost)
+		if _, ok := right.(*goast.UnaryExpr); ok && types.IsDereferenceType(rightType) {
+			deref, err := types.GetDereferenceType(rightType)
 
-		} else {
-			right, err = types.CastExpr(p, right, rightType, returnType)
+			if !p.AddMessage(p.GenerateWarningMessage(err, n)) {
+				resolvedDeref, err := types.ResolveType(p, deref)
 
-			if _, ok := right.(*goast.UnaryExpr); ok && types.IsDereferenceType(rightType) {
-				deref, err := types.GetDereferenceType(rightType)
+				// FIXME: I'm not sure how this situation arises.
+				if resolvedDeref == "" {
+					resolvedDeref = "interface{}"
+				}
 
 				if !p.AddMessage(p.GenerateWarningMessage(err, n)) {
-					resolvedDeref, err := types.ResolveType(p, deref)
-
-					// FIXME: I'm not sure how this situation arises.
-					if resolvedDeref == "" {
-						resolvedDeref = "interface{}"
-					}
-
-					if !p.AddMessage(p.GenerateWarningMessage(err, n)) {
-						p.AddImport("unsafe")
-						right = util.CreateSliceFromReference(resolvedDeref, right)
-					}
+					p.AddImport("unsafe")
+					right = CreateSliceFromReference(resolvedDeref, right)
 				}
 			}
+		}
 
-			if p.AddMessage(p.GenerateWarningMessage(err, n)) && right == nil {
-				right = util.NewNil()
-			}
-
+		if p.AddMessage(p.GenerateWarningMessage(err, n)) && right == nil {
+			right = util.NewNil()
 		}
 	}
 
@@ -543,88 +590,3 @@ func foundCallExpr(n ast.Node) *ast.CallExpr {
 	}
 	return nil
 }
-
-// getAllocationSizeNode returns the node that, if evaluated, would return the
-// size (in bytes) of a memory allocation operation. For example:
-//
-//     (int *)malloc(sizeof(int))
-//
-// Would return the node that represents the "sizeof(int)".
-//
-// If the node does not represent an allocation operation (such as calling
-// malloc, calloc, realloc, etc.) then nil is returned.
-//
-// In the case of calloc() it will return a new BinaryExpr that multiplies both
-// arguments.
-func getAllocationSizeNode(p *program.Program, node ast.Node) ast.Node {
-	expr := foundCallExpr(node)
-
-	if expr == nil || expr == (*ast.CallExpr)(nil) {
-		return nil
-	}
-
-	functionName, err := getName(p, expr)
-	p.AddMessage(p.GenerateWarningMessage(err, node))
-
-	if functionName == "malloc" {
-		// Is 1 always the body in this case? Might need to be more careful
-		// to find the correct node.
-		return expr.Children()[1]
-	}
-
-	if functionName == "calloc" {
-		return &ast.BinaryOperator{
-			Type:       "int",
-			Operator:   "*",
-			ChildNodes: expr.Children()[1:],
-		}
-	}
-
-	// TODO: realloc() is not supported
-	// https://github.com/Konstantin8105/c4go/issues/118
-	//
-	// Realloc will be treated as calloc which will almost certainly cause
-	// bugs in your code.
-	if functionName == "realloc" {
-		return expr.Children()[2]
-	}
-
-	return nil
-}
-
-func generateAlloc(p *program.Program, allocSize ast.Node, leftType string) (
-	right goast.Expr, preStmts []goast.Stmt, postStmts []goast.Stmt, err error) {
-
-	allocSizeExpr, _, newPre, newPost, err := transpileToExpr(allocSize, p, false)
-
-	preStmts, postStmts = combinePreAndPostStmts(preStmts, postStmts, newPre, newPost)
-
-	if err != nil {
-		return nil, preStmts, postStmts, err
-	}
-
-	derefType, err := types.GetDereferenceType(leftType)
-	if err != nil {
-		return nil, preStmts, postStmts, err
-	}
-
-	toType, err := types.ResolveType(p, leftType)
-	if err != nil {
-		return nil, preStmts, postStmts, err
-	}
-	if toType == "interface{}" {
-		toType = "[]byte"
-	}
-
-	elementSize, err := types.SizeOf(p, derefType)
-	if err != nil {
-		return nil, preStmts, postStmts, err
-	}
-
-	right = util.NewCallExpr(
-		"make",
-		util.NewTypeIdent(toType),
-		util.NewBinaryExpr(allocSizeExpr, token.QUO, util.NewIntLit(elementSize), "int", false),
-	)
-	return
-}
diff --git a/transpiler/call.go b/transpiler/call.go
index 9a6a959..cbf0554 100644
--- a/transpiler/call.go
+++ b/transpiler/call.go
@@ -234,23 +234,20 @@ func transpileCallExpr(n *ast.CallExpr, p *program.Program) (
 	if p.IncludeHeaderIsExists("stdlib.h") {
 		if functionName == "malloc" && len(n.Children()) == 2 {
 			// Change from "malloc" to "calloc"
-			n.ChildNodes[0] = &ast.ImplicitCastExpr{
-				Type: "void *(*)(unsigned long, unsigned long)",
+			unary, expression, back, err := findAndReplaceUnaryExprOrTypeTraitExpr(&n.Children()[1])
+			if err != nil {
+				back()
+				return transpileCallExprCalloc(n.Children()[1],
+					&ast.UnaryExprOrTypeTraitExpr{
+						Function: "sizeof",
+						Type1:    "unsigned long",
+						Type2:    "char",
+					}, p)
 			}
-			n.ChildNodes[0].(*ast.ImplicitCastExpr).AddChild(&ast.DeclRefExpr{
-				Type: "void *(unsigned long, unsigned long)",
-				Name: "calloc",
-			})
-			n.AddChild(&ast.UnaryExprOrTypeTraitExpr{
-				Type1:    "unsigned long",
-				Function: "sizeof",
-				Type2:    "char",
-			})
-			return transpileCallExprCalloc(n, p)
+			return transpileCallExprCalloc(expression, unary.(*ast.UnaryExprOrTypeTraitExpr), p)
 		}
 	}
 
-	// function "realloc" from stdlib.h
 	//
 	// Change from "realloc" to "calloc"
 	//
@@ -303,14 +300,36 @@ func transpileCallExpr(n *ast.CallExpr, p *program.Program) (
 				Type2:    sizeofType,
 			})
 			n.ChildNodes = []ast.Node{n.ChildNodes[0], n.ChildNodes[2], n.ChildNodes[3]}
-			return transpileCallExprCalloc(n, p)
+			return transpileCallExpr(n, p)
 		}
 	}
 
 	// function "calloc" from stdlib.h
 	if p.IncludeHeaderIsExists("stdlib.h") {
 		if functionName == "calloc" && len(n.Children()) == 3 {
-			return transpileCallExprCalloc(n, p)
+			if unary, ok := n.Children()[2].(*ast.UnaryExprOrTypeTraitExpr); ok {
+				return transpileCallExprCalloc(n.Children()[1], unary, p)
+			}
+
+			call := &ast.CallExpr{}
+
+			call.AddChild(&ast.ImplicitCastExpr{
+				Type: "void *(*)(unsigned long)",
+			})
+			call.ChildNodes[0].(*ast.ImplicitCastExpr).AddChild(&ast.DeclRefExpr{
+				Type: "void *(unsigned long)",
+				Name: "malloc",
+			})
+
+			bin := &ast.BinaryOperator{
+				Operator: "*",
+				Type:     "unsigned long",
+			}
+			bin.AddChild(n.ChildNodes[1])
+			bin.AddChild(n.ChildNodes[2])
+			call.AddChild(bin)
+
+			return transpileCallExpr(call, p)
 		}
 	}
 
@@ -596,79 +615,102 @@ func transpileCallExpr(n *ast.CallExpr, p *program.Program) (
 		functionDef.ReturnType, preStmts, postStmts, nil
 }
 
-func transpileCallExprCalloc(n *ast.CallExpr, p *program.Program) (
-	expr *goast.CallExpr, resultType string, preStmts []goast.Stmt, postStmts []goast.Stmt, err error) {
+func findAndReplaceUnaryExprOrTypeTraitExpr(node *ast.Node) (
+	unary ast.Node, tree ast.Node, back func(), err error) {
+
 	defer func() {
 		if err != nil {
-			err = fmt.Errorf("Function: calloc. err = %v", err)
+			err = fmt.Errorf("Cannot findAndReplaceUnaryExprOrTypeTraitExpr: err = %v", err)
+			if (*node) != nil {
+				err = fmt.Errorf("Code line: %d. %v", (*node).Position().Line, err)
+			}
 		}
 	}()
-	size, sizeType, preStmts, postStmts, err := transpileToExpr(n.Children()[1], p, false)
-	if err != nil {
-		return nil, "", nil, nil, err
+
+	var counter int
+	var lastNode *ast.Node
+	one := &ast.IntegerLiteral{Type: "int", Value: "1"}
+
+	var searcher func(*ast.Node) bool
+	replacer := func(node *ast.Node) {
+		unary = *node
+		lastNode = node
+		*node = one
+		counter++
 	}
-	size, err = types.CastExpr(p, size, sizeType, "unsigned long")
-	if err != nil {
-		return nil, "", nil, nil, err
+	searcher = func(node *ast.Node) (modify bool) {
+		// find
+		if u, ok := (*node).(*ast.UnaryExprOrTypeTraitExpr); ok &&
+			u.Function == "sizeof" {
+			return true
+		}
+		for i := range (*node).Children() {
+			if searcher(&((*node).Children()[i])) {
+				replacer(&((*node).Children()[i]))
+			}
+		}
+		return false
+	}
+	if searcher(node) {
+		unary = *node
+		lastNode = node
+		*node = one
+		counter++
 	}
 
-	//
-	// -UnaryExprOrTypeTraitExpr 0x24e0498 <col:27, col:39> 'unsigned long' sizeof 'float'
-	//
-	// OR
-	//
-	// t.w = (float*) calloc(t.nw, sizeof(*t.w));
-	// -UnaryExprOrTypeTraitExpr <> 'unsigned long' sizeof
-	//  `-ParenExpr <> 'float' lvalue
-	//    `-UnaryOperator <> 'float' lvalue prefix '*'
-	//      `-ImplicitCastExpr <> 'float *' <LValueToRValue>
-	//        `-MemberExpr <> 'float *' lvalue .w 0x2548b38
-	//          `-DeclRefExpr <> 'struct cws':'struct cws' lvalue Var 0x2548c40 't' 'struct cws': 'struct cws'
-	//
-	// OR
-	//
-	// CallExpr <> 'void *'
-	// |-ImplicitCastExpr <> 'void *(*)(unsigned long, unsigned long)' <FunctionToPointerDecay>
-	// | `-DeclRefExpr <> 'void *(unsigned long, unsigned long)' Function 0x3b9b048 'calloc' 'void *(unsigned long, unsigned long)'
-	// |-ImplicitCastExpr <> 'unsigned long' <IntegralCast>
-	// | `-ImplicitCastExpr <> 'int' <LValueToRValue>
-	// |   `-DeclRefExpr <> 'int' lvalue ParmVar 0x3bc40d8 'n' 'int'
-	// `-ImplicitCastExpr <> 'unsigned long' <IntegralCast>
-	//   `-ImplicitCastExpr <> 'int' <LValueToRValue>
-	//     `-DeclRefExpr <> 'int' lvalue Var 0x3bc4268 'sizeT' 'int'
-	var goType goast.Expr
-	switch v := n.Children()[2].(type) {
-	case *ast.UnaryExprOrTypeTraitExpr:
-		var t string
-		if v.Type2 == "" {
-			_, t, _, _, _ = transpileToExpr(v.Children()[0], p, false)
-		} else {
-			t = v.Type2
-		}
-		t, err := types.ResolveType(p, t)
-		if err != nil {
-			return nil, "", nil, nil, err
+	back = func() {
+		// return back node
+		if unary != nil {
+			*lastNode = unary
 		}
-		goType = &goast.ArrayType{Elt: goast.NewIdent(t)}
-	default:
-		var goTypeT string
-		goType, goTypeT, _, _, _ = transpileToExpr(v.Children()[0], p, false)
-		size, err = types.CastExpr(p, size, sizeType, goTypeT)
+	}
+
+	if counter != 1 {
+		err = fmt.Errorf("counter is not 1: %d", counter)
+		return
+	}
+	if unary == nil {
+		err = fmt.Errorf("pointer is nil")
+		return
+	}
+
+	tree = *node
+
+	return
+}
+
+//
+// calloc nodes:
+// [0] - function identification
+// [1] - expression
+// [2] - type UnaryExprOrTypeTraitExpr always
+func transpileCallExprCalloc(expression ast.Node, unary *ast.UnaryExprOrTypeTraitExpr, p *program.Program) (
+	expr *goast.CallExpr, resultType string, preStmts []goast.Stmt, postStmts []goast.Stmt, err error) {
+	defer func() {
 		if err != nil {
-			return nil, "", nil, nil, err
-		}
-		size = &goast.BinaryExpr{
-			X:  &goast.ParenExpr{X: goType},
-			Op: token.MUL,
-			Y:  &goast.ParenExpr{X: size},
-		}
-		goType = &goast.ArrayType{
-			Elt: goast.NewIdent("byte"),
+			err = fmt.Errorf("Function: calloc. err = %v", err)
 		}
+	}()
+
+	size, _, newPre, newPost, err := atomicOperation(expression, p)
+	if err != nil {
+		return
+	}
+	preStmts, postStmts = combinePreAndPostStmts(preStmts, postStmts, newPre, newPost)
+
+	var t string = unary.Type2
+	if t == "" {
+		_, t, _, _, _ = transpileToExpr(unary, p, false)
+	}
+	resultType = t + "*"
+	t, err = types.ResolveType(p, t)
+	if err != nil {
+		return nil, "", nil, nil, err
 	}
+	goType := &goast.ArrayType{Elt: goast.NewIdent(t)}
 
 	return util.NewCallExpr("make", goType, size),
-		n.Type, preStmts, postStmts, nil
+		resultType, preStmts, postStmts, nil
 }
 
 func transpileCallExprQsort(n *ast.CallExpr, p *program.Program) (
diff --git a/transpiler/cast.go b/transpiler/cast.go
index 0f63315..480156a 100644
--- a/transpiler/cast.go
+++ b/transpiler/cast.go
@@ -20,6 +20,9 @@ func transpileImplicitCastExpr(n *ast.ImplicitCastExpr, p *program.Program, expr
 		if err != nil {
 			err = fmt.Errorf("Cannot transpileImplicitCastExpr. err = %v", err)
 		}
+		if exprType == "" {
+			exprType = "ImplicitCastExprWrongType"
+		}
 	}()
 
 	n.Type = util.GenerateCorrectType(n.Type)
@@ -40,6 +43,18 @@ func transpileImplicitCastExpr(n *ast.ImplicitCastExpr, p *program.Program, expr
 		expr = goast.NewIdent("nil")
 		return
 	}
+
+	// type casting
+	if n.Kind == "BitCast" && types.IsPointer(exprType, p) && types.IsPointer(n.Type, p) {
+		var newPost []goast.Stmt
+		expr, exprType, newPost, err = PntBitCast(expr, exprType, n.Type, p)
+		postStmts = append(postStmts, newPost...)
+		if err != nil {
+			return nil, "BitCastWrongType", nil, nil, err
+		}
+		return
+	}
+
 	if n.Kind == "IntegralToPointer" {
 		// ImplicitCastExpr 'double *' <IntegralToPointer>
 		// `-ImplicitCastExpr 'long' <LValueToRValue>
@@ -180,6 +195,9 @@ func transpileCStyleCastExpr(n *ast.CStyleCastExpr, p *program.Program, exprIsSt
 		if err != nil {
 			err = fmt.Errorf("Cannot transpileImplicitCastExpr. err = %v", err)
 		}
+		if exprType == "" {
+			exprType = "CStyleCastExpr"
+		}
 	}()
 
 	n.Type = util.GenerateCorrectType(n.Type)
@@ -232,6 +250,17 @@ func transpileCStyleCastExpr(n *ast.CStyleCastExpr, p *program.Program, exprIsSt
 		return
 	}
 
+	// type casting
+	if n.Kind == "BitCast" && types.IsPointer(exprType, p) && types.IsPointer(n.Type, p) {
+		var newPost []goast.Stmt
+		expr, exprType, newPost, err = PntBitCast(expr, exprType, n.Type, p)
+		postStmts = append(postStmts, newPost...)
+		if err != nil {
+			return nil, "BitCastWrongType", nil, nil, err
+		}
+		return
+	}
+
 	if len(n.Type) != 0 && len(n.Type2) != 0 && n.Type != n.Type2 {
 		var tt string
 		tt, err = types.ResolveType(p, n.Type)
@@ -272,8 +301,13 @@ func transpileCStyleCastExpr(n *ast.CStyleCastExpr, p *program.Program, exprIsSt
 					if err != nil {
 						return nil, "", nil, nil, err
 					}
-					var retType string
-					expr, retType = util.GetUintptrForSlice(expr, sizeof)
+					var retType string = "long long"
+					var newPost []goast.Stmt
+					expr, newPost, err = GetPointerAddress(expr, *t, sizeof)
+					if err != nil {
+						return nil, "", nil, nil, err
+					}
+					postStmts = append(postStmts, newPost...)
 
 					expr, err = types.CastExpr(p, expr, retType, n.Type)
 					if err != nil {
diff --git a/transpiler/operators.go b/transpiler/operators.go
index 3a4c840..620ac51 100644
--- a/transpiler/operators.go
+++ b/transpiler/operators.go
@@ -4,15 +4,9 @@
 package transpiler
 
 import (
-	"bytes"
 	"fmt"
-	"go/parser"
-	"go/printer"
-	"go/token"
-	"html/template"
-	"strings"
-
 	goast "go/ast"
+	"go/token"
 
 	"github.com/Konstantin8105/c4go/ast"
 	"github.com/Konstantin8105/c4go/program"
@@ -213,134 +207,6 @@ func transpileParenExpr(n *ast.ParenExpr, p *program.Program) (
 	return
 }
 
-// pointerArithmetic - operations between 'int' and pointer
-// Example C code : ptr += i
-// ptr = (*(*[1]int)(unsafe.Pointer(uintptr(unsafe.Pointer(&ptr[0])) + (i)*unsafe.Sizeof(ptr[0]))))[:]
-// , where i  - right
-//        '+' - operator
-//      'ptr' - left
-//      'int' - leftType transpiled in Go type
-// Note:
-// 1) rigthType MUST be 'int'
-// 2) pointerArithmetic - implemented ONLY right part of formula
-// 3) right is MUST be positive value, because impossible multiply uintptr to (-1)
-func pointerArithmetic(p *program.Program,
-	left goast.Expr, leftType string,
-	right goast.Expr, rightType string,
-	operator token.Token) (
-	_ goast.Expr, _ string, preStmts []goast.Stmt, postStmts []goast.Stmt, err error) {
-	defer func() {
-		if err != nil {
-			err = fmt.Errorf("Cannot transpile pointerArithmetic. err = %v", err)
-		}
-	}()
-
-	if bl, ok := right.(*goast.BasicLit); ok && operator == token.ADD {
-		if bl.Value == "1" && bl.Kind == token.INT {
-			return &goast.SliceExpr{
-				X:      left,
-				Lbrack: 1,
-				Low: &goast.BasicLit{
-					Kind:  token.INT,
-					Value: "1",
-				},
-				Slice3: false,
-			}, leftType, preStmts, postStmts, nil
-		}
-	}
-
-	if !(types.IsCInteger(p, rightType) || rightType == "bool") {
-		err = fmt.Errorf("right type is not C integer type : '%s'", rightType)
-		return
-	}
-	if !types.IsPointer(leftType, p) {
-		err = fmt.Errorf("left type is not a pointer : '%s'", leftType)
-		return
-	}
-	right, err = types.CastExpr(p, right, rightType, "int")
-	if err != nil {
-		return
-	}
-
-	for {
-		if t, ok := p.TypedefType[leftType]; ok {
-			leftType = t
-			continue
-		}
-		break
-	}
-
-	resolvedLeftType, err := types.ResolveType(p, leftType)
-	if err != nil {
-		return
-	}
-
-	type pA struct {
-		Name      string // name of variable: 'ptr'
-		Type      string // type of variable: 'int','double'
-		Condition string // condition : '-1' ,'(-1+2-2)'
-		Operator  string // operator : '+', '-'
-	}
-
-	var s pA
-
-	{
-		var buf bytes.Buffer
-		_ = printer.Fprint(&buf, token.NewFileSet(), left)
-		s.Name = buf.String()
-	}
-	{
-		var buf bytes.Buffer
-		_ = printer.Fprint(&buf, token.NewFileSet(), right)
-		s.Condition = buf.String()
-	}
-
-	s.Type = resolvedLeftType
-	if resolvedLeftType != "interface{}" {
-		s.Type = resolvedLeftType[2:]
-	}
-
-	s.Operator = "+"
-	if operator == token.SUB {
-		s.Operator = "-"
-	}
-
-	src := `package main
-func main(){
-	a := (*(*[1000000000]{{ .Type }})(unsafe.Pointer(uintptr(
-			unsafe.Pointer(&{{ .Name }}[0])) {{ .Operator }}
-			(uintptr)({{ .Condition }})*unsafe.Sizeof({{ .Name }}[0]))))[:]
-}`
-	tmpl := template.Must(template.New("").Parse(src))
-	var source bytes.Buffer
-	err = tmpl.Execute(&source, s)
-	if err != nil {
-		err = fmt.Errorf("Cannot execute template. err = %v", err)
-		return
-	}
-
-	// Create the AST by parsing src.
-	fset := token.NewFileSet() // positions are relative to fset
-	body := strings.Replace(source.String(), "&#43;", "+", -1)
-	body = strings.Replace(body, "&amp;", "&", -1)
-	body = strings.Replace(body, "&#34;", "\"", -1)
-	body = strings.Replace(body, "&#39;", "'", -1)
-	body = strings.Replace(body, "&gt;", ">", -1)
-	body = strings.Replace(body, "&lt;", "<", -1)
-	// TODO: add unicode convertor
-	f, err := parser.ParseFile(fset, "", body, 0)
-	if err != nil {
-		body = strings.Replace(body, "\n", "", -1)
-		err = fmt.Errorf("Cannot parse file. err = %v. body = `%s`", err, body)
-		return
-	}
-
-	p.AddImport("unsafe")
-
-	return f.Decls[0].(*goast.FuncDecl).Body.List[0].(*goast.AssignStmt).Rhs[0],
-		leftType, preStmts, postStmts, nil
-}
-
 func transpileCompoundAssignOperator(
 	n *ast.CompoundAssignOperator, p *program.Program, exprIsStmt bool) (
 	_ goast.Expr, _ string, preStmts []goast.Stmt, postStmts []goast.Stmt, err error) {
@@ -874,6 +740,9 @@ func atomicOperation(n ast.Node, p *program.Program) (
 		if v.Kind == "IntegralToPointer" {
 			return
 		}
+		if v.Kind == "BitCast" {
+			return
+		}
 
 		// avoid problem :
 		//
diff --git a/transpiler/unary.go b/transpiler/unary.go
index c5ed008..0b7d5c7 100644
--- a/transpiler/unary.go
+++ b/transpiler/unary.go
@@ -279,7 +279,7 @@ func transpileUnaryOperatorAmpersant(n *ast.UnaryOperator, p *program.Program) (
 		return
 	}
 
-	expr = util.CreateSliceFromReference(resolvedType, expr)
+	expr = CreateSliceFromReference(resolvedType, expr)
 
 	return
 }
diff --git a/transpiler/value_to_pointer.go b/transpiler/value_to_pointer.go
index abb13d3..5f7b029 100644
--- a/transpiler/value_to_pointer.go
+++ b/transpiler/value_to_pointer.go
@@ -1,11 +1,15 @@
 package transpiler
 
 import (
+	"bytes"
 	"fmt"
+	goast "go/ast"
+	"go/parser"
+	"go/printer"
 	"go/token"
+	"html/template"
 	"sort"
-
-	goast "go/ast"
+	"strings"
 
 	"github.com/Konstantin8105/c4go/ast"
 	"github.com/Konstantin8105/c4go/program"
@@ -137,3 +141,546 @@ func GetUnsafeConvertDecls(p *program.Program) {
 
 	return
 }
+
+// ---------------- POINTER OPERATIONS ---------------------------------------
+// Examples:
+//	1) pointer + integer - integer
+//	2) pointer1 > pointer2
+//	3) pointer1 == pointer2
+//	4) pointer1 - pointer2
+//	5) pointer to integer address
+//	6) integer address to pointer
+//	7) pointerType1 to pointerType2
+//
+// Simplification:
+//	1) pointer +/- integer
+//	2) (pointer1 - pointer2) >  0
+//	3) (pointer1 - pointer2) == 0
+//	4) (pointer1 - pointer2)
+//	5) pointer to integer address
+//	6) integer address to pointer
+//	7) pointerType1 to integer address to pointerType2
+//
+
+// GetPointerAddress - return goast expression with pointer address.
+// 		pnt       - goast expression. Foe example: `&a`, `&a[11]`.
+//		sizeof    - sizeof of C type.
+//		rs        - result goast expression.
+//		postStmts - slice of goast.Stmt for runtime.KeepAlive of pointer,
+//		            the best way kept that stmts at the end of function.
+//		            Each stmt has `defer` functions.
+func GetPointerAddress(expr goast.Expr, cType string, sizeof int) (
+	rs goast.Expr, postStmts []goast.Stmt, err error) {
+
+	// generate postStmts
+
+	// TODO: runtime.KeepAlive()
+
+	if par, ok := expr.(*goast.ParenExpr); ok {
+		// ignore parens
+		return GetPointerAddress(par.X, cType, sizeof)
+	}
+
+	if id, ok := expr.(*goast.Ident); ok {
+		if id.Name == "nil" {
+			// nil pointer
+			rs = goast.NewIdent("0")
+			return
+		}
+	}
+
+	if _, ok := expr.(*goast.Ident); ok {
+		expr = &goast.IndexExpr{
+			X:     expr,
+			Index: goast.NewIdent("0"),
+		}
+	}
+
+	if _, ok := expr.(*goast.SelectorExpr); ok {
+		expr = &goast.IndexExpr{
+			X:     expr,
+			Index: goast.NewIdent("0"),
+		}
+	}
+
+	if sl, ok := expr.(*goast.SliceExpr); ok {
+		// from :
+		//
+		// 88  0: *ast.SliceExpr {
+		// 89  .  X: *ast.Ident {
+		// 91  .  .  Name: "b"
+		// 93  .  }
+		// 95  .  Low: *ast.BasicLit { ... }
+		// 99  .  }
+		// 102  }
+		//
+		// to:
+		//
+		// 0  *ast.IndexExpr {
+		// 1  .  X: *ast.Ident {
+		// 3  .  .  Name: "b"
+		// 4  .  }
+		// 6  .  Index: *ast.BasicLit { ... }
+		// 12  }
+		if sl.Low == nil {
+			sl.Low = goast.NewIdent("0")
+		}
+		util.PanicIfNil(sl.X, "slice is nil")
+		util.PanicIfNil(sl.Low, "slice low is nil")
+		expr = &goast.IndexExpr{
+			X:     sl.X,
+			Index: sl.Low,
+		}
+	}
+
+	if sl, ok := expr.(*goast.SliceExpr); ok {
+		if c, ok := sl.X.(*goast.CallExpr); ok {
+			if fin, ok := c.Fun.(*goast.Ident); ok && strings.Contains(fin.Name, "1000000") {
+				if len(c.Args) == 1 {
+					if cc, ok := c.Args[0].(*goast.CallExpr); ok {
+						if fin, ok := cc.Fun.(*goast.Ident); ok && strings.Contains(fin.Name, "unsafe.Pointer") {
+							if len(cc.Args) == 1 {
+								if un, ok := cc.Args[0].(*goast.UnaryExpr); ok && un.Op == token.AND {
+									expr = un.X
+								}
+							}
+						}
+					}
+				}
+			}
+		}
+	}
+
+	if _, ok := expr.(*goast.CallExpr); ok {
+		name := "c4go_temp_name"
+		rs = util.NewAnonymousFunction(
+			// body
+			[]goast.Stmt{
+				&goast.ExprStmt{
+					X: &goast.BinaryExpr{
+						X:  goast.NewIdent(name),
+						Op: token.DEFINE,
+						Y:  expr,
+					},
+				},
+			},
+			// defer
+			nil,
+			// returnValue
+			util.NewCallExpr("int64", util.NewCallExpr("uintptr", util.NewCallExpr("unsafe.Pointer",
+				&goast.StarExpr{
+					Star: 1,
+					X: &goast.CallExpr{
+						Fun:    goast.NewIdent("(**byte)"),
+						Lparen: 1,
+						Args: []goast.Expr{&goast.CallExpr{
+							Fun:    goast.NewIdent("unsafe.Pointer"),
+							Lparen: 1,
+							Args: []goast.Expr{
+								&goast.UnaryExpr{
+									Op: token.AND,
+									X:  goast.NewIdent(name),
+								},
+							},
+						}},
+					},
+				},
+			))),
+			// returnType
+			"int64",
+		)
+		return
+	}
+
+	// prepare postStmts
+
+	if sizeof < 1 {
+		err = fmt.Errorf("Not valid sizeof `%s`: %d", cType, sizeof)
+		return
+	}
+
+	// main result expression
+	rs = &goast.BinaryExpr{
+		X: util.NewCallExpr("int64", util.NewCallExpr("uintptr",
+			util.NewCallExpr("unsafe.Pointer",
+				&goast.UnaryExpr{Op: token.AND, X: expr},
+			),
+		)),
+		Op: token.QUO,
+		Y:  util.NewCallExpr("int64", goast.NewIdent(fmt.Sprintf("%d", sizeof))),
+	}
+
+	// return results
+	return
+}
+
+//	SubTwoPnts function for implementation : (pointer1 - pointer2)
+func SubTwoPnts(
+	val1 goast.Expr, val1Type string,
+	val2 goast.Expr, val2Type string,
+	sizeof int) (rs goast.Expr, postStmts []goast.Stmt, err error) {
+
+	x, newPost, err := GetPointerAddress(val1, val1Type, sizeof)
+	if err != nil {
+		return
+	}
+	postStmts = append(postStmts, newPost...)
+
+	y, newPost, err := GetPointerAddress(val2, val2Type, sizeof)
+	if err != nil {
+		return
+	}
+	postStmts = append(postStmts, newPost...)
+
+	rs = &goast.ParenExpr{X: &goast.BinaryExpr{X: x, Op: token.SUB, Y: y}}
+
+	return
+}
+
+//		postStmts - slice of goast.Stmt for runtime.KeepAlive of pointer,
+//		            the best way kept that stmts at the end of function.
+//		            Each stmt has `defer` functions.
+func PntCmpPnt(
+	p *program.Program,
+	val1 goast.Expr, val1Type string,
+	val2 goast.Expr, val2Type string,
+	sizeof int, operator token.Token,
+) (
+	rs goast.Expr,
+	postStmts []goast.Stmt,
+	err error,
+) {
+
+	switch operator {
+	case token.SUB: // -
+		p.AddImport("unsafe")
+		sub, newPost, err := SubTwoPnts(val1, val1Type, val2, val2Type, sizeof)
+		postStmts = append(postStmts, newPost...)
+		return sub, postStmts, err
+	case token.LAND, token.LOR: // && ||
+		// TODO: add tests
+		p.AddImport("unsafe")
+		var newPost []goast.Stmt
+		val1, newPost, err = PntCmpPnt(
+			p,
+			val1, val1Type,
+			goast.NewIdent("nil"), types.NullPointer,
+			sizeof, token.EQL)
+		if err != nil {
+			return
+		}
+		postStmts = append(postStmts, newPost...)
+		val2, newPost, err = PntCmpPnt(
+			p,
+			val2, val2Type,
+			goast.NewIdent("nil"), types.NullPointer,
+			sizeof, token.EQL)
+		if err != nil {
+			return
+		}
+		postStmts = append(postStmts, newPost...)
+		rs = &goast.BinaryExpr{
+			X:  val1,
+			Op: operator,
+			Y:  val2,
+		}
+		return
+	}
+
+	// > >= > <= ==
+
+	{
+		// specific for operations with nil
+		isExprNil := func(node goast.Expr) bool {
+			id, ok := node.(*goast.Ident)
+			if !ok {
+				return false
+			}
+			if id.Name != "nil" {
+				return false
+			}
+			return true
+		}
+
+		if !(isExprNil(val1) && isExprNil(val2)) {
+			// Examples:
+			// val1 != nil
+			// val1 == nil
+			// val1  > nil
+
+			ignoreList := func(Type string) bool {
+				return util.IsFunction(Type) ||
+					Type == types.NullPointer ||
+					Type == "void *" ||
+					Type == "FILE *"
+			}
+
+			switch {
+			case isExprNil(val2):
+				if !ignoreList(val1Type) {
+					val1 = util.NewCallExpr("len", val1)
+					val2 = goast.NewIdent("0")
+				}
+				rs = &goast.BinaryExpr{
+					X:  val1,
+					Op: operator,
+					Y:  val2,
+				}
+				return
+
+			case isExprNil(val1):
+				if !ignoreList(val2Type) {
+					val1 = goast.NewIdent("0")
+					val2 = util.NewCallExpr("len", val2)
+				}
+				rs = &goast.BinaryExpr{
+					X:  val1,
+					Op: operator,
+					Y:  val2,
+				}
+				return
+			}
+		}
+	}
+
+	p.AddImport("unsafe")
+	sub, newPost, err := SubTwoPnts(val1, val1Type, val2, val2Type, sizeof)
+	postStmts = append(postStmts, newPost...)
+
+	rs = &goast.BinaryExpr{
+		X:  sub,
+		Op: operator,
+		Y:  goast.NewIdent("0"),
+	}
+
+	return
+}
+
+// PntBitCast - casting pointers
+func PntBitCast(expr goast.Expr, cFrom, cTo string, p *program.Program) (
+	rs goast.Expr, toCtype string, postStmts []goast.Stmt, err error) {
+	defer func() {
+		if err != nil {
+			err = fmt.Errorf("Cannot PntBitCast : %v", err)
+			p.AddMessage(p.GenerateWarningMessage(err, nil))
+		}
+	}()
+
+	cFrom = util.GenerateCorrectType(cFrom)
+	cTo = util.GenerateCorrectType(cTo)
+	toCtype = cTo
+
+	if !types.IsPointer(cFrom, p) || !types.IsPointer(cTo, p) {
+		err = fmt.Errorf("Some type is not pointer `%s` or `%s`", cFrom, cTo)
+		return
+	}
+
+	rs = expr
+
+	if cFrom == cTo {
+		// no need cast
+		return
+	}
+
+	if util.IsFunction(cFrom) {
+		return
+	}
+
+	{
+		from, errf := types.ResolveType(p, cFrom)
+		to, errto := types.ResolveType(p, cTo)
+		if from == to && errf == nil && errto == nil {
+			// no need cast
+			return
+		}
+	}
+
+	if cTo == "void *" {
+		// no need cast
+		return
+	}
+
+	if cFrom == "void *" {
+		// no need cast
+		rs, err = types.CastExpr(p, expr, cFrom, cTo)
+		return
+	}
+
+	rs, postStmts, err = GetPointerAddress(expr, cFrom, 1)
+	if err != nil {
+		return
+	}
+	resolvedType, err := types.ResolveType(p, cTo)
+	if err != nil {
+		return
+	}
+
+	resolvedType = strings.Replace(resolvedType, "[]", "[1000000]", 1)
+
+	p.AddImport("unsafe")
+	rs = util.NewCallExpr("(*"+resolvedType+")", util.NewCallExpr("unsafe.Pointer",
+		util.NewCallExpr("uintptr", rs)))
+
+	rs = &goast.SliceExpr{
+		X:      rs,
+		Slice3: false,
+	}
+
+	return
+}
+
+// CreateSliceFromReference - create a slice, like :
+// (*[1]int)(unsafe.Pointer(&a))[:]
+func CreateSliceFromReference(goType string, expr goast.Expr) goast.Expr {
+	// If the Go type is blank it means that the C type is 'void'.
+	if goType == "" {
+		goType = "interface{}"
+	}
+
+	// This is a hack to convert a reference to a variable into a slice that
+	// points to the same location. It will look similar to:
+	//
+	//     (*[1]int)(unsafe.Pointer(&a))[:]
+	//
+	// You must always call this Go before using CreateSliceFromReference:
+	//
+	//     p.AddImport("unsafe")
+	//
+	return &goast.SliceExpr{
+		X: util.NewCallExpr(fmt.Sprintf("(*[1000000]%s)", goType),
+			util.NewCallExpr("unsafe.Pointer",
+				&goast.UnaryExpr{
+					X:  expr,
+					Op: token.AND,
+				}),
+		),
+	}
+}
+
+// pointerArithmetic - operations between 'int' and pointer
+// Example C code : ptr += i
+// ptr = (*(*[1]int)(unsafe.Pointer(uintptr(unsafe.Pointer(&ptr[0])) + (i)*unsafe.Sizeof(ptr[0]))))[:]
+// , where i  - right
+//        '+' - operator
+//      'ptr' - left
+//      'int' - leftType transpiled in Go type
+// Note:
+// 1) rigthType MUST be 'int'
+// 2) pointerArithmetic - implemented ONLY right part of formula
+// 3) right is MUST be positive value, because impossible multiply uintptr to (-1)
+func pointerArithmetic(p *program.Program,
+	left goast.Expr, leftType string,
+	right goast.Expr, rightType string,
+	operator token.Token) (
+	_ goast.Expr, _ string, preStmts []goast.Stmt, postStmts []goast.Stmt, err error) {
+	defer func() {
+		if err != nil {
+			err = fmt.Errorf("Cannot transpile pointerArithmetic. err = %v", err)
+		}
+	}()
+
+	if bl, ok := right.(*goast.BasicLit); ok && operator == token.ADD {
+		if bl.Value == "1" && bl.Kind == token.INT {
+			return &goast.SliceExpr{
+				X:      left,
+				Lbrack: 1,
+				Low: &goast.BasicLit{
+					Kind:  token.INT,
+					Value: "1",
+				},
+				Slice3: false,
+			}, leftType, preStmts, postStmts, nil
+		}
+	}
+
+	if !(types.IsCInteger(p, rightType) || rightType == "bool") {
+		err = fmt.Errorf("right type is not C integer type : '%s'", rightType)
+		return
+	}
+	if !types.IsPointer(leftType, p) {
+		err = fmt.Errorf("left type is not a pointer : '%s'", leftType)
+		return
+	}
+	right, err = types.CastExpr(p, right, rightType, "int")
+	if err != nil {
+		return
+	}
+
+	for {
+		if t, ok := p.TypedefType[leftType]; ok {
+			leftType = t
+			continue
+		}
+		break
+	}
+
+	resolvedLeftType, err := types.ResolveType(p, leftType)
+	if err != nil {
+		return
+	}
+
+	type pA struct {
+		Name      string // name of variable: 'ptr'
+		Type      string // type of variable: 'int','double'
+		Condition string // condition : '-1' ,'(-1+2-2)'
+		Operator  string // operator : '+', '-'
+	}
+
+	var s pA
+
+	{
+		var buf bytes.Buffer
+		_ = printer.Fprint(&buf, token.NewFileSet(), left)
+		s.Name = buf.String()
+	}
+	{
+		var buf bytes.Buffer
+		_ = printer.Fprint(&buf, token.NewFileSet(), right)
+		s.Condition = buf.String()
+	}
+
+	s.Type = resolvedLeftType
+	if resolvedLeftType != "interface{}" {
+		s.Type = resolvedLeftType[2:]
+	}
+
+	s.Operator = "+"
+	if operator == token.SUB {
+		s.Operator = "-"
+	}
+
+	src := `package main
+func main(){
+	a := (*(*[1000000]{{ .Type }})(unsafe.Pointer(uintptr(
+			unsafe.Pointer(&{{ .Name }}[0])) {{ .Operator }}
+			(uintptr)({{ .Condition }})*unsafe.Sizeof({{ .Name }}[0]))))[:]
+}`
+	tmpl := template.Must(template.New("").Parse(src))
+	var source bytes.Buffer
+	err = tmpl.Execute(&source, s)
+	if err != nil {
+		err = fmt.Errorf("Cannot execute template. err = %v", err)
+		return
+	}
+
+	// Create the AST by parsing src.
+	fset := token.NewFileSet() // positions are relative to fset
+	body := strings.Replace(source.String(), "&#43;", "+", -1)
+	body = strings.Replace(body, "&amp;", "&", -1)
+	body = strings.Replace(body, "&#34;", "\"", -1)
+	body = strings.Replace(body, "&#39;", "'", -1)
+	body = strings.Replace(body, "&gt;", ">", -1)
+	body = strings.Replace(body, "&lt;", "<", -1)
+	// TODO: add unicode convertor
+	f, err := parser.ParseFile(fset, "", body, 0)
+	if err != nil {
+		body = strings.Replace(body, "\n", "", -1)
+		err = fmt.Errorf("Cannot parse file. err = %v. body = `%s`", err, body)
+		return
+	}
+
+	p.AddImport("unsafe")
+
+	return f.Decls[0].(*goast.FuncDecl).Body.List[0].(*goast.AssignStmt).Rhs[0],
+		leftType, preStmts, postStmts, nil
+}
diff --git a/transpiler/variables.go b/transpiler/variables.go
index 3dc09c4..27a5e1b 100644
--- a/transpiler/variables.go
+++ b/transpiler/variables.go
@@ -60,27 +60,6 @@ func getDefaultValueForVar(p *program.Program, a *ast.VarDecl) (
 		return nil, "", nil, nil, nil
 	}
 
-	// Memory allocation is translated into the Go-style.
-	if allocSize := getAllocationSizeNode(p, a.Children()[0]); allocSize != nil {
-		// type
-		var t string
-		if v, ok := a.Children()[0].(*ast.ImplicitCastExpr); ok {
-			t = v.Type
-		}
-		if v, ok := a.Children()[0].(*ast.CStyleCastExpr); ok {
-			t = v.Type
-		}
-		if t != "" {
-			right, newPre, newPost, err := generateAlloc(p, allocSize, t)
-			if err != nil {
-				p.AddMessage(p.GenerateWarningMessage(err, a))
-				return nil, "", nil, nil, err
-			}
-
-			return []goast.Expr{right}, t, newPre, newPost, nil
-		}
-	}
-
 	if va, ok := a.Children()[0].(*ast.VAArgExpr); ok {
 		outType, err := types.ResolveType(p, va.Type)
 		if err != nil {
@@ -318,6 +297,38 @@ func transpileArraySubscriptExpr(n *ast.ArraySubscriptExpr, p *program.Program)
 
 	children := n.Children()
 
+	if un, ok := children[1].(*ast.UnaryOperator); ok && un.Operator == "-" && un.IsPrefix {
+		// from:
+		//  ArraySubscriptExpr 'double' lvalue
+		//  |-ImplicitCastExpr 'double *' <LValueToRValue>
+		//  | `-DeclRefExpr 'double *' lvalue Var 0x2d19e58 'p' 'double *'
+		//  `-UnaryOperator 'int' prefix '-'
+		//    `-IntegerLiteral 'int' 1
+		// to:
+		//  BinaryOperator 'double *' '-'
+		//  |-ImplicitCastExpr 'double *' <LValueToRValue>
+		//  | `-DeclRefExpr 'double *' lvalue Var 0x2d19e58 'p' 'double *'
+		//  `-IntegerLiteral 'int' 1
+
+		t, ok := ast.GetTypeIfExist(children[0])
+		if ok {
+			bin := &ast.BinaryOperator{
+				Type:     *t,
+				Operator: "-",
+			}
+			bin.AddChild(n.Children()[0])
+			bin.AddChild(un.Children()[0])
+
+			expression, _, newPre, newPost, err := atomicOperation(bin, p)
+			preStmts, postStmts = combinePreAndPostStmts(preStmts, postStmts, newPre, newPost)
+
+			return &goast.IndexExpr{
+				X:     expression,
+				Index: goast.NewIdent("0"),
+			}, n.Type, preStmts, postStmts, err
+		}
+	}
+
 	expression, _, newPre, newPost, err := transpileToExpr(children[0], p, false)
 	if err != nil {
 		return nil, "", nil, nil, err
diff --git a/types/sizeof.go b/types/sizeof.go
index e44a092..10cc7af 100644
--- a/types/sizeof.go
+++ b/types/sizeof.go
@@ -84,7 +84,14 @@ func SizeOf(p *program.Program, cType string) (size int, err error) {
 	}
 
 	// An union will be the max size of its parts.
-	if strings.HasPrefix(cType, "union ") {
+	var isUnion bool
+	cType = util.GenerateCorrectType(cType)
+	if _, ok := p.Unions[cType]; ok {
+		isUnion = true
+	} else if _, ok := p.Unions["union "+cType]; ok {
+		isUnion = true
+	}
+	if isUnion {
 		byteCount := 0
 
 		s := p.Unions[cType]
diff --git a/util/goast.go b/util/goast.go
index e074c4e..c175fe4 100644
--- a/util/goast.go
+++ b/util/goast.go
@@ -190,13 +190,15 @@ func NewBinaryExpr(left goast.Expr, operator token.Token, right goast.Expr,
 	return b
 }
 
+const C4GoPostFixForAvoid string = "_c4go_postfix"
+
 // NewIdent - create a new Go ast Ident
 func NewIdent(name string) *goast.Ident {
 	// TODO: The name of a variable or field cannot be a reserved word
 	// https://github.com/Konstantin8105/c4go/issues/83
 	// Search for this issue in other areas of the codebase.
 	if IsGoKeyword(name) {
-		name += "_"
+		name += C4GoPostFixForAvoid
 	}
 
 	// Remove const prefix as it has no equivalent in Go.
@@ -302,178 +304,6 @@ func ConvertFunctionNameFromCtoGo(name string) string {
 	return name
 }
 
-// GetUintptr - return uintptr. Example : uintptr(unsafe.Pointer(&expr))
-func GetUintptr(expr goast.Expr) goast.Expr {
-
-	if _, ok := expr.(*goast.SelectorExpr); ok {
-		expr = &goast.IndexExpr{
-			X:     expr,
-			Index: goast.NewIdent("0"),
-		}
-	}
-
-	if sl, ok := expr.(*goast.SliceExpr); ok {
-		// from :
-		//
-		// 88  0: *ast.SliceExpr {
-		// 89  .  X: *ast.Ident {
-		// 91  .  .  Name: "b"
-		// 93  .  }
-		// 95  .  Low: *ast.BasicLit { ... }
-		// 99  .  }
-		// 102  }
-		//
-		// to:
-		//
-		// 0  *ast.IndexExpr {
-		// 1  .  X: *ast.Ident {
-		// 3  .  .  Name: "b"
-		// 4  .  }
-		// 6  .  Index: *ast.BasicLit { ... }
-		// 12  }
-		if sl.Low == nil {
-			sl.Low = goast.NewIdent("0")
-		}
-		PanicIfNil(sl.X, "slice is nil")
-		PanicIfNil(sl.Low, "slice low is nil")
-		expr = &goast.IndexExpr{
-			X:     sl.X,
-			Index: sl.Low,
-		}
-	}
-
-	if sl, ok := expr.(*goast.SliceExpr); ok {
-		if c, ok := sl.X.(*goast.CallExpr); ok {
-			if fin, ok := c.Fun.(*goast.Ident); ok && strings.Contains(fin.Name, "100000") {
-				if len(c.Args) == 1 {
-					if cc, ok := c.Args[0].(*goast.CallExpr); ok {
-						if fin, ok := cc.Fun.(*goast.Ident); ok && strings.Contains(fin.Name, "unsafe.Pointer") {
-							if len(cc.Args) == 1 {
-								if un, ok := cc.Args[0].(*goast.UnaryExpr); ok && un.Op == token.AND {
-									expr = un.X
-								}
-							}
-						}
-					}
-				}
-			}
-		}
-	}
-
-	return NewCallExpr("uintptr",
-		NewCallExpr("unsafe.Pointer",
-			&goast.UnaryExpr{
-				Op: token.AND,
-				X:  expr,
-			},
-		),
-	)
-}
-
-// GetUintptrForSlice - return uintptr for slice
-// Example : uint64(uintptr(unsafe.Pointer((*(**int)(unsafe.Pointer(& ...slice... )))))))
-func GetUintptrForSlice(expr goast.Expr, sizeof int) (goast.Expr, string) {
-	returnType := "long long"
-
-	if sl, ok := expr.(*goast.SliceExpr); ok {
-		expr = &goast.IndexExpr{
-			X:     sl.X,
-			Index: sl.Low,
-		}
-	}
-
-	if _, ok := expr.(*goast.CallExpr); ok {
-		name := "c4go_temp_name"
-		expr = NewAnonymousFunction(
-			// body
-			[]goast.Stmt{
-				&goast.ExprStmt{
-					X: &goast.BinaryExpr{
-						X:  goast.NewIdent(name),
-						Op: token.DEFINE,
-						Y:  expr,
-					},
-				},
-			},
-			// defer
-			nil,
-			// returnValue
-			NewCallExpr("int64", NewCallExpr("uintptr", NewCallExpr("unsafe.Pointer",
-				&goast.StarExpr{
-					Star: 1,
-					X: &goast.CallExpr{
-						Fun:    goast.NewIdent("(**byte)"),
-						Lparen: 1,
-						Args: []goast.Expr{&goast.CallExpr{
-							Fun:    goast.NewIdent("unsafe.Pointer"),
-							Lparen: 1,
-							Args: []goast.Expr{
-								&goast.UnaryExpr{
-									Op: token.AND,
-									X:  goast.NewIdent(name),
-								},
-							},
-						}},
-					},
-				},
-			))),
-			// returnType
-			"int64",
-		)
-		return expr, returnType
-	}
-
-	return &goast.BinaryExpr{
-		X: NewCallExpr("int64", NewCallExpr("uintptr", NewCallExpr("unsafe.Pointer",
-			&goast.StarExpr{
-				Star: 1,
-				X: &goast.CallExpr{
-					Fun:    goast.NewIdent("(**byte)"),
-					Lparen: 1,
-					Args: []goast.Expr{&goast.CallExpr{
-						Fun:    goast.NewIdent("unsafe.Pointer"),
-						Lparen: 1,
-						Args: []goast.Expr{&goast.UnaryExpr{
-							Op: token.AND,
-							X:  expr,
-						}},
-					}},
-				},
-			},
-		))),
-		Op: token.QUO,
-		Y:  NewCallExpr("int64", goast.NewIdent(fmt.Sprintf("%d", sizeof))),
-	}, returnType
-}
-
-// CreateSliceFromReference - create a slice, like :
-// (*[1]int)(unsafe.Pointer(&a))[:]
-func CreateSliceFromReference(goType string, expr goast.Expr) goast.Expr {
-	// If the Go type is blank it means that the C type is 'void'.
-	if goType == "" {
-		goType = "interface{}"
-	}
-
-	// This is a hack to convert a reference to a variable into a slice that
-	// points to the same location. It will look similar to:
-	//
-	//     (*[1]int)(unsafe.Pointer(&a))[:]
-	//
-	// You must always call this Go before using CreateSliceFromReference:
-	//
-	//     p.AddImport("unsafe")
-	//
-	return &goast.SliceExpr{
-		X: NewCallExpr(fmt.Sprintf("(*[100000000]%s)", goType),
-			NewCallExpr("unsafe.Pointer",
-				&goast.UnaryExpr{
-					X:  expr,
-					Op: token.AND,
-				}),
-		),
-	}
-}
-
 // NewFuncType - create a new function type, example:
 // func ...(fieldList)(returnType)
 func NewFuncType(fieldList *goast.FieldList, returnType string, addDefaultReturn bool) *goast.FuncType {


Test patch:
diff --git a/other_test.go b/other_test.go
index 01bb38f..f88f7c1 100644
--- a/other_test.go
+++ b/other_test.go
@@ -700,12 +700,14 @@ func TestKiloEditor(t *testing.T) {
 	}
 
 	// calculate amount unsafe operations
-	if count := bytes.Count(dat, []byte("unsafe.Pointer")); count > 54 {
+	unsafeLimit := 29
+	uintptrLimit := 18
+	if count := bytes.Count(dat, []byte("unsafe.Pointer")); count > unsafeLimit {
 		t.Fatalf("too much unsafe operations: %d", count)
 	} else {
 		t.Logf("amount unsafe operations: %d", count)
 	}
-	if count := bytes.Count(dat, []byte("uintptr")); count > 12 {
+	if count := bytes.Count(dat, []byte("uintptr")); count > uintptrLimit {
 		t.Fatalf("too much uintptr operations: %d", count)
 	} else {
 		t.Logf("amount uintptr operations: %d", count)
diff --git a/tests/array.c b/tests/array.c
index 3e2f0a9..7e0bddb 100644
--- a/tests/array.c
+++ b/tests/array.c
@@ -675,9 +675,48 @@ void test_func_byte()
 	trans(gameOver2);
 }
 
+void test_negative_index()
+{
+	double ad[5] = {1.,2., 4., 5.,6.0};
+	is_eq(ad[0], 1.0);
+	double *p = ad;
+	p += 3;
+	is_eq(*p,5.0);
+	is_eq(p[-1],4.0);
+	double *ds = &(p[-1]);
+	is_eq(ds[-1], 2.0);
+}
+
+void test_matrix_init()
+{
+	int rows = 2;
+	int cols = 3;
+	int      i,j;
+	double   **m;
+
+	m = (double **) malloc( (unsigned) rows * sizeof(double *) );
+	for (i = 0; i < rows ; i++)
+	{
+		m[i] = (double *) malloc( (unsigned) cols * sizeof(double) );
+	}
+
+	for (i = 0; i < rows ; i++){
+		for (j = 0; j < cols; j++){
+			printf("init [%d , %d]\n",i,j);
+			m[i][j] = i*cols + j;
+		}
+	}
+
+	for (i = 0; i < rows ; i++){
+		for (j = 0; j < cols; j++){
+			is_eq(m[i][j] , i*cols + j);
+		}
+	}
+}
+
 int main()
 {
-    plan(184);
+    plan(194);
 
     test_parg_struct();
     START_TEST(struct_init);
@@ -1214,6 +1253,8 @@ int main()
     START_TEST(string_array);
     START_TEST(double_array);
 	START_TEST(func_byte);
+	START_TEST(negative_index);
+	START_TEST(matrix_init);
 
     done_testing();
 }
diff --git a/tests/cast.c b/tests/cast.c
index 83e5e24..248a8c1 100644
--- a/tests/cast.c
+++ b/tests/cast.c
@@ -1,5 +1,6 @@
 #include "tests.h"
 #include <stdio.h>
+#include <stdlib.h>
 
 #define START_TEST(t) \
     diag(#t);         \
diff --git a/tests/code_quality/ap.go.expected b/tests/code_quality/ap.go.expected
index d53ec63..1fd3eb5 100644
--- a/tests/code_quality/ap.go.expected
+++ b/tests/code_quality/ap.go.expected
@@ -58,7 +58,7 @@ func main() {
 	a(i6)
 	b(i6, 1)
 	var val int32 = 2 - 2
-	var i7 []int32 = (*(*[1000000000]int32)(unsafe.Pointer(uintptr(unsafe.Pointer(&(*(*[1000000000]int32)(unsafe.Pointer(uintptr(unsafe.Pointer(&(*(*[1000000000]int32)(unsafe.Pointer(uintptr(unsafe.Pointer(&i5[0])) + (uintptr)(1+(1-1)+val+0*(100-2))*unsafe.Sizeof(i5[0]))))[:][0])) + (uintptr)(0)*unsafe.Sizeof((*(*[1000000000]int32)(unsafe.Pointer(uintptr(unsafe.Pointer(&i5[0])) + (uintptr)(1+(1-1)+val+0*(100-2))*unsafe.Sizeof(i5[0]))))[:][0]))))[:][0])) - (uintptr)(0*0)*unsafe.Sizeof((*(*[1000000000]int32)(unsafe.Pointer(uintptr(unsafe.Pointer(&(*(*[1000000000]int32)(unsafe.Pointer(uintptr(unsafe.Pointer(&i5[0])) + (uintptr)(1+(1-1)+val+0*(100-2))*unsafe.Sizeof(i5[0]))))[:][0])) + (uintptr)(0)*unsafe.Sizeof((*(*[1000000000]int32)(unsafe.Pointer(uintptr(unsafe.Pointer(&i5[0])) + (uintptr)(1+(1-1)+val+0*(100-2))*unsafe.Sizeof(i5[0]))))[:][0]))))[:][0]))))[:]
+	var i7 []int32 = (*(*[1000000]int32)(unsafe.Pointer(uintptr(unsafe.Pointer(&(*(*[1000000]int32)(unsafe.Pointer(uintptr(unsafe.Pointer(&(*(*[1000000]int32)(unsafe.Pointer(uintptr(unsafe.Pointer(&i5[0])) + (uintptr)(1+(1-1)+val+0*(100-2))*unsafe.Sizeof(i5[0]))))[:][0])) + (uintptr)(0)*unsafe.Sizeof((*(*[1000000]int32)(unsafe.Pointer(uintptr(unsafe.Pointer(&i5[0])) + (uintptr)(1+(1-1)+val+0*(100-2))*unsafe.Sizeof(i5[0]))))[:][0]))))[:][0])) - (uintptr)(0*0)*unsafe.Sizeof((*(*[1000000]int32)(unsafe.Pointer(uintptr(unsafe.Pointer(&(*(*[1000000]int32)(unsafe.Pointer(uintptr(unsafe.Pointer(&i5[0])) + (uintptr)(1+(1-1)+val+0*(100-2))*unsafe.Sizeof(i5[0]))))[:][0])) + (uintptr)(0)*unsafe.Sizeof((*(*[1000000]int32)(unsafe.Pointer(uintptr(unsafe.Pointer(&i5[0])) + (uintptr)(1+(1-1)+val+0*(100-2))*unsafe.Sizeof(i5[0]))))[:][0]))))[:][0]))))[:]
 	// pointer arithmetic
 	a(i7)
 	b(i7, 1)
@@ -74,7 +74,7 @@ func main() {
 	// pointer arithmetic
 	a(i10)
 	b(i10, 1)
-	var i11 []int32 = (*(*[1000000000]int32)(unsafe.Pointer(uintptr(unsafe.Pointer(&i5[1+0+0+5*get()+get():][0])) - (uintptr)((12+3)*get())*unsafe.Sizeof(i5[1+0+0+5*get()+get():][0]))))[:]
+	var i11 []int32 = (*(*[1000000]int32)(unsafe.Pointer(uintptr(unsafe.Pointer(&i5[1+0+0+5*get()+get():][0])) - (uintptr)((12+3)*get())*unsafe.Sizeof(i5[1+0+0+5*get()+get():][0]))))[:]
 	// pointer arithmetic
 	a(i11)
 	b(i11, 1)
diff --git a/tests/code_quality/stdio.go.expected b/tests/code_quality/stdio.go.expected
index e892e80..df01ad0 100644
--- a/tests/code_quality/stdio.go.expected
+++ b/tests/code_quality/stdio.go.expected
@@ -10,8 +10,8 @@ package code_quality
 import "github.com/Konstantin8105/c4go/noarch"
 import "fmt"
 
-// print - transpiled function from  C4GO/tests/code_quality/stdio.c:3
-func print() {
+// print_ - transpiled function from  C4GO/tests/code_quality/stdio.c:3
+func print_() {
 	fmt.Printf("Hello")
 	noarch.Printf([]byte("Hello, %d\x00"), 42)
 }
diff --git a/tests/if.c b/tests/if.c
index 8e89739..e460c19 100644
--- a/tests/if.c
+++ b/tests/if.c
@@ -1,5 +1,6 @@
 #include "tests.h"
 #include <stdio.h>
+#include <stdlib.h>
 
 int d(int v)
 {
diff --git a/tests/operators.c b/tests/operators.c
index 3c6a71a..fc6c8cd 100644
--- a/tests/operators.c
+++ b/tests/operators.c
@@ -76,7 +76,7 @@ struct UUU000{
 
 int main()
 {
-    plan(158);
+    plan(160);
 
 	is_eq(valGlobInt, 42);
 	is_eq(valGlobDouble, 45);
@@ -510,10 +510,9 @@ int main()
     diag("compare char pointer");
     {
         char* b = "happy new code";
-        char* c = b[3];
-        if (c < b) {
-            pass("ok");
-        }
+		is_true(&b[3] >  &b[0]);
+		is_true(&b[3] == &b[3]);
+		is_true(&b[3] <  &b[4]);
     }
     diag("kilo.c example");
     {
@@ -693,6 +692,14 @@ int main()
 			break;
 		}
 	}
+	diag("pointer with & ");
+	{
+		double a = 43;
+		double * ptr = &a;
+		int pos = (int)((unsigned long) (ptr) & (unsigned long) 3l);
+		(void) pos;
+		(void) ptr;
+	}
 
     done_testing();
 }
diff --git a/tests/sizeof.c b/tests/sizeof.c
index fdbc54f..cb2a382 100644
--- a/tests/sizeof.c
+++ b/tests/sizeof.c
@@ -22,13 +22,13 @@
     printf("%s = (%d) %d bytes\n", #v, p, sizeof(v));
 
 struct MyStruct {
-    double a;
+    double a,aa,aaa,aaaa;
     char b;
     char c;
 };
 
 union MyUnion {
-    double a;
+    long double a;
     char b;
     int c;
 };
@@ -44,7 +44,7 @@ struct MyNums {
 
 int main()
 {
-    plan(55);
+    plan(58);
 
     diag("Integer types");
     check_sizes(char, 1);
@@ -67,6 +67,7 @@ int main()
     is_eq(sizeof(char*), 8);
     is_eq(sizeof(char*), 8);
     is_eq(sizeof(short**), 8);
+    is_eq(sizeof(long double**), 8);
 
     diag("Variables");
     a = 123;
@@ -78,14 +79,16 @@ int main()
 
     is_eq(sizeof(a), 2);
     is_eq(sizeof(b), 4);
-    is_eq(sizeof(s1), 16);
-    is_eq(sizeof(u1), 8);
+    is_eq(sizeof(s1), 40);
+    is_eq(sizeof(u1), 16);
 
     diag("Structures");
-    is_eq(sizeof(struct MyStruct), 16);
+    is_eq(sizeof(struct MyStruct), 40);
+    is_eq(sizeof(struct MyStruct *), 8);
 
     diag("Unions");
-    is_eq(sizeof(union MyUnion), 8);
+    is_eq(sizeof(union MyUnion), 16);
+    is_eq(sizeof(union MyUnion *), 8);
 
     diag("Function pointers");
     is_eq(sizeof(main), 1);
diff --git a/tests/stdlib.c b/tests/stdlib.c
index 297ade5..0f47b8f 100644
--- a/tests/stdlib.c
+++ b/tests/stdlib.c
@@ -203,6 +203,7 @@ void* cs_calloc(int n)
 {
     int sizeT = sizeof(int);
     return (n < 2 ? NULL : calloc(n, sizeT));
+	(void) sizeT;
 }
 
 void test_calloc2()