import std.stdio;
import std.c.stdio;
import std.range;
import std.array;
import std.functional;
import std.algorithm;
import std.conv;
import std.container;
import std.math;
import std.numeric;
import std.string;
import std.c.string;
import std.regex;
import std.typecons;

struct Edge {
    int from, to;
    int cost;
}

struct State {
    int v;
    int cost;
    int opCmp(const ref State s) const {
        return cost - s.cost;
    }
}

void main() {
    int N, M, K;
    readf("%d %d %d\n", &N, &M, &K);
    Edge[][] G = new Edge[][N];
    foreach (i; 0 .. M) {
        int a, b, l; readf("%d %d %d\n", &a, &b, &l);
        a--; b--;
        G[a] ~= Edge(a, b, l);
        G[b] ~= Edge(b, a, l);
    }
    int[] D = new int[N];
    D[] = int.max / 2;
    BinaryHeap!(Array!State, "a > b") Q;
    foreach (i; 0 .. K) {
        int s; readf("%d\n", &s);
        s--;
        D[s] = 0; 
        Q.insert(State(s, 0));
    }
    // dijkstra
    while (!Q.empty) {
        State s = Q.front; Q.removeFront;
        foreach (e; G[s.v]) {
            if (D[e.to] > D[s.v] + e.cost) {
                D[e.to] = D[s.v] + e.cost;
                Q.insert(State(e.to, D[e.to]));
            }
        }
    }
    int ans = 0;
    foreach (i; 0 .. N) {
        ans = max(ans, D[i]);
    }
    foreach (i; 0 .. N) {
        foreach (e; G[i]) {
            static int div2(int x) {
                return (x + 1) / 2;
            }
            ans = max(ans, div2(D[e.from] + D[e.to] + e.cost));
        }
    }
    ans.writeln;
}