//* Problem  : 1185 - Wall
//* Contest  : acm.timus.ru
//* Type     : Solution
//* Date     : 2007.11.15
//* Author   : alt
//* Language : C++
//* Compiler : Microsoft Visual C++ 6.0

//* Computational Geometry Library by Alt
//* Started @ 06.10.2007

#include <stdio.h>
#include <math.h>
#include <string.h>
#include <stdlib.h>

#define MIN(a, b) (a<b?a:b)
#define MAX(a, b) (a>b?a:b)
#define PI 2.0 * acos(0.0)


//#define COORD_TYPE_FLOAT
#define COORD_TYPE int
#define EPS 10E-9
#define INF 1E100

struct point{
	COORD_TYPE x, y;
	int used;
} a[1000], b[1000];

struct segment{
	point p1, p2;
};

struct polygon{
	int n;
	point a[101];
} border;


int r[300][300];

int n, L;
double res;

void solve();
void result();

int main()
{
	scanf("%d%d", &n, &L);
	for (int i = 0; i < n; i++)
		scanf("%d%d", &a[i].x, &a[i].y);
	solve();
	result();
	return 0;
}

/////////////////////////////////////////////////////////////////////////////////////////////////////////////////
///
///                                       Library
///
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////

COORD_TYPE X(point p1, point p2)
{
	return p1.x * p2.y - p1.y * p2.x;
} 

int CollinearPoints(point p1, point p2, point p3)
{
	//(x2 - x1) * (y3 - y1) = (x3 - x1) * (y2 - y1)
	return ((p2.x - p1.x) * (p3.y - p1.y) == (p3.x - p1.x) * (p2.y - p1.y));
}

int Point_On_Segment(segment s, point p)
{
	if (!CollinearPoints(s.p1, s.p2, p)) return 0;
	return (p.x >= MIN(s.p1.x, s.p2.x) && p.x <= MAX(s.p1.x, s.p2.x) &&
			p.y >= MIN(s.p1.y, s.p2.y) && p.y <= MAX(s.p1.y, s.p2.y));
}


double distance_point_to_point(point p1, point p2)
{
	COORD_TYPE dx = p1.x - p2.x, dy = p1.y - p2.y;
	return (sqrt(1.0 * dx * dx + dy * dy));
}

double distance_from_point_to_segment(segment l, point p)
{
	// Check if segment is just a single point
	if (l.p1.x == l.p2.x && l.p1.y == l.p2.y) return distance_point_to_point(p, l.p2);
	// Otherwise
	double  d = distance_point_to_point(l.p1, l.p2);
	double d1 = distance_point_to_point(l.p1, p);
	double d2 = distance_point_to_point(l.p2, p);
	if (d2*d2 > d1*d1 + d*d) return d1;
	else if (d1*d1 > d2*d2 + d*d) return d2;
	else if (d >= d1 +  d2) return 0.0;
	double p2 = (d+d1+d2)/2.0;
	double s = sqrt(p2*(p2-d)*(p2-d1)*(p2-d2));
	return (2.0*s/d);
}

//  0 - on segment
//  1 - left
// -1 - right
//  2 - on line but not on segment
int orientation_point_segment(segment s, point p)
{
	double x, y, x1, y1, x2, y2;
	x = p.x; y = p.y;
	x1 = s.p1.x; y1 = s.p1.y;
	x2 = s.p2.x; y2 = s.p2.y;
	double k = (x-x2)*(y1-y2) - (y-y2)*(x1-x2);
	if (k < -EPS) return -1;
		else if (k > EPS) return 1;
	if (((x<=x1 && x>=x2) || (x>=x1 && x<=x2))&&((y<=y1 && y>=y2) || (y>=y1 && y<=y2)))
		return 0;
	return  2;
}


int Point_Inside_On_Borded_Of_Polygon(polygon pl, point p)
{
	int sign[100], i, nn = pl.n, sum = 0; segment t;
	for (i = 0; i < nn; i++)
	{
		t.p1 = pl.a[i]; t.p2 = pl.a[(i+1)%nn];
		sign[i] = orientation_point_segment(t, p);
		sum += sign[i];
		// on border
		if (!sign[i]) return 1;
	}
	if (sum == nn * sign[0] && abs(sign[0]) == 1) return 1;
	return 0;
}

int Point_Belongs_Line(segment l, point p)
{
	return CollinearPoints(l.p1, l.p2, p);
}

int Point_Belongs_Segment(segment s, point p)
{
	if (!CollinearPoints(s.p1, s.p2, p)) return 0;
	//(x - x1) * (x - x2) < 0) ((y - y1) * (y - y2) < 0).
	return ((p.x - s.p1.x) *  (p.x - s.p2.x) <= 0 && (p.y - s.p1.y) *  (p.y - s.p2.y) <= 0);
}


int Lines_Intersection_Coord(segment s1, segment s2, point *res)
{
	COORD_TYPE a1, a2, b1, b2, c1, c2, d, dx, dy;
	a1 = s1.p2.y - s1.p1.y; b1 = s1.p1.x - s1.p2.x;
	c1 = s1.p1.y * (s1.p2.x - s1.p1.x) - s1.p1.x * (s1.p2.y - s1.p1.y);
	a2 = s2.p2.y - s2.p1.y; b2 = s2.p1.x - s2.p2.x;
	c2 = s2.p1.y * (s2.p2.x - s2.p1.x) - s2.p1.x * (s2.p2.y - s2.p1.y);
	c1 = -c1; c2 = -c2;
	d = a1 * b2 - a2 * b1;
	if (!d) return 0;
	dx = c1 * b2 - c2 * b1;
	dy = a1 * c2 - c1 * a2;
	res->x = dx / d; res->y = dy / d;
	return 1;
}


int Segments_Intersection_Coord(segment s1, segment s2, point *res)
{
	point t;
	if (!Lines_Intersection_Coord(s1, s2, &t)) return 0;
	if (Point_Belongs_Segment(s1, t) && Point_Belongs_Segment(s2, t))
	{
		res->x = t.x; res->y = t.y;
		return 1;
	}
	else return 0;
}

int vect(point a1, point a2, point b1, point b2)
{
	return (a2.x - a1.x) * (b2.y - b1.y) - (b2.x - b1.x) * (a2.y - a1.y);
}

int len2(point p1, point p2)
{
	return (p1.x - p2.x) * (p1.x - p2.x) + (p1.y - p2.y) * (p1.y - p2.y);
}


void convex_hull(point a[], int na, point b[], int *nb)
{
	int m, i, j, k, min;
	// LR point
	m = 0;
	for (i = 1; i < n; i++)
		if ((a[i].y < a[m].y) || (a[i].y == a[m].y && a[i].x > a[m].x)) m = i;
	b[0] = a[m]; a[m] = a[0]; a[0] = b[0];
	a[m].used = 1;
	k = 0; min = 1;
	do
	{
		for (j = 1; j < n; j++)
			if (
				(vect(b[k], a[min], b[k], a[j]) < 0) || 
				(vect(b[k],a[min],b[k],a[j]) == 0) && len2(b[k],a[min]) < len2(b[k],a[j])
			)
				min = j;
		b[++k] = a[min];
		a[min].used = 1;
		min = 0;
	}
	while (b[k].x != b[0].x || b[k].y != b[0].y);
	*nb = k;

}

/////////////////////////////////////////////////////////////////////////////////////////////////////////////////
///
///                                         AdHoc
///
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////


void solve()
{
	int nb; res = 0.0;
	convex_hull(a, n, b, &nb);
	for (int i = 0; i < nb - 1; i++)
		res += distance_point_to_point(b[i], b[i + 1]);
	res += distance_point_to_point(b[0], b[nb - 1]);
	res += 2 * PI * L;
}

void result()
{
	printf("%.0lf\n", res);
}


