Okay, first let us look at your foo function.
Here you have a Promise that has resolved to a Promise. What the async function declaration does is effectively making the function return a promise.
This means you can then use await inside the async function without worrying about the function resolution. For example:
// Lets say you have a 'long running' function that returns a promise.
const timeout = ms =>  new Promise(
    resolve => setTimeout(resolve, ms)
);
// What you can do is something like so:
async function foo(args) {
    await timeout(500);
    console.log(args);
    return args;
}
The 'timeout' function came from @Bergi.
This does almost exactly the same thing as your first foo function.
// Lets say you 'foo' here.
const fooPromise = foo('Your args');
// The output here would be a pending Promise
// in chrome console: Promise {<pending>}
What your foo code does, is effectively the same, except it in practice does something like this:
function foo(args) {
    return new Promise(resolve1 => {
        return new Promise((resolve, reject) => {
            setTimeout(() => {
                console.log(args)
                resolve(args)
            }, 500)
        });
    });
}
This is rather redundant, but does not adversely affect how the program runs.
Secondly, let us look at the init function.
In JavaScript you don't need to use an 'Init', 'Main' or any equivalent.
You can just start running your code, so your init code could be removed from the function and executed like so:
var params = [10, 20, 30];
var promises = [];
for (let x of params) {
    promises.push(foo(x));
}
//do something with Promise.all(promises) here
Now to making the Promises, again, there is nothing really 'wrong' with your code.
In order to use 'Promise.all' here you simply pass the promises array to Promise.all as you commented.
Promise.all returns a Promise that will contain an array of your generated promises. You can then access that the same way you'd access any other Promise.
// Use your promises
Promise.all(promises)
// Do what you need to do with the Promises
.then(output => {
    // Output = [10, 20, 30]
});
Your code using the 'for loop' can be replaced using an Array.prototype.map to quickly produce an array of promises, like so:
var params = [10, 20, 30];
Promise.all(params.map(foo))
.then(output => {
    // Output = [10, 20, 30]
});
Putting this together you would use the promises like so:
// A 'long running' function that returns a promise.
const timeout = ms =>  new Promise(
    resolve => setTimeout(resolve, ms)
);
// What you can do is something like so:
async function foo(args) {
    // A 'long running' function that returns a promise.
    await timeout(500);
    // Here you can manipulate the args like normal
    // e.g.:
    args = args ** 2;
    console.log(args);
    return args;
}
var params = [10, 20, 30];
Promise.all(params.map(foo))
.then(output => {
    // output = [100, 400, 900]
    console.log(output);
});
The output of this would be:
100
400
900
[100, 400, 900]
In your console.